mirror of
https://github.com/facebook/react.git
synced 2025-11-01 09:12:30 +00:00
Fixtures for control values that become reactive due to interleaving
See the previous PR, interleaved mutation can cause values that were not reactive to become reactive. I swear I had a case where this was observable, but I came up with it before reordering the PRs in this stack. I think my repro relied on an immutable reference to a mutable value, which is now handled in InferReactivePlaces. So here i'm just adding fixtures, and allowing this case since it's unobservable.
This commit is contained in:
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(false);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x = 0;
|
||||
do {
|
||||
x += 1;
|
||||
} while (c[0][0]);
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(false);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x = 0;
|
||||
do {
|
||||
x = x + 1;
|
||||
} while (c[0][0]);
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(false);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x = 0;
|
||||
do {
|
||||
x += 1;
|
||||
} while (c[0][0]);
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push({ a: false });
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i in c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push({ a: false });
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i in c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push({ a: false });
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i in c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(0);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = c[0][0]; i < 10; i++) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(0);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = c[0][0]; i < 10; i++) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(0);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = c[0][0]; i < 10; i++) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i of c[0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i of c[0]) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (const i of c[0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < c[0][0]; i++) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < c[0][0]; i++) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < c[0][0]; i++) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < 10; i += c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < 10; i = i + c[0][0], i) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(10);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
for (let i = 0; i < 10; i += c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+3
-3
@@ -17,7 +17,7 @@ function Component(props) {
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
if (c[0]) {
|
||||
if (c[0][0]) {
|
||||
x = 1;
|
||||
} else {
|
||||
x = 2;
|
||||
@@ -51,7 +51,7 @@ function Component(props) {
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
if (c[0]) {
|
||||
if (c[0][0]) {
|
||||
x = 1;
|
||||
} else {
|
||||
x = 2;
|
||||
@@ -74,4 +74,4 @@ export const FIXTURE_ENTRYPOINT = {
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [1]
|
||||
(kind: ok) [2]
|
||||
+1
-1
@@ -13,7 +13,7 @@ function Component(props) {
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
if (c[0]) {
|
||||
if (c[0][0]) {
|
||||
x = 1;
|
||||
} else {
|
||||
x = 2;
|
||||
|
||||
+85
@@ -0,0 +1,85 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
switch (c[0][0]) {
|
||||
case true: {
|
||||
x = 1;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
x = 2;
|
||||
}
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
bb1: switch (c[0][0]) {
|
||||
case true: {
|
||||
x = 1;
|
||||
break bb1;
|
||||
}
|
||||
default: {
|
||||
x = 2;
|
||||
}
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [2]
|
||||
+35
@@ -0,0 +1,35 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
switch (c[0][0]) {
|
||||
case true: {
|
||||
x = 1;
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
x = 2;
|
||||
}
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
+73
@@ -0,0 +1,73 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
while (c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { unstable_useMemoCache as useMemoCache } from "react";
|
||||
function Component(props) {
|
||||
const $ = useMemoCache(1);
|
||||
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
while (c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = [x];
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) [null]
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
function Component(props) {
|
||||
// a and b are independent but their mutations are interleaved, so
|
||||
// they get grouped in a reactive scope. this means that a becomes
|
||||
// reactive since it will effectively re-evaluate based on a reactive
|
||||
// input
|
||||
const a = [];
|
||||
const b = [];
|
||||
b.push(props.cond);
|
||||
a.push(null);
|
||||
|
||||
// Downstream consumer of a, which initially seems non-reactive except
|
||||
// that a becomes reactive, per above
|
||||
const c = [a];
|
||||
|
||||
let x;
|
||||
while (c[0][0]) {
|
||||
x = 1;
|
||||
}
|
||||
// The values assigned to `x` are non-reactive, but the value of `x`
|
||||
// depends on the "control" value `c[0]` which becomes reactive via
|
||||
// being interleaved with `b`.
|
||||
// Therefore x should be treated as reactive too.
|
||||
return [x];
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: Component,
|
||||
params: [{ cond: true }],
|
||||
};
|
||||
Reference in New Issue
Block a user