Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
90cf7bba08 | ||
|
|
c19f052b2d | ||
|
|
d2d5350e65 |
@@ -1143,7 +1143,7 @@ function checkFunctionReferencedBeforeDeclarationAtTopLevel(
|
||||
* A null scope means there's no function scope, which means we're at the
|
||||
* top level scope.
|
||||
*/
|
||||
if (scope === null) {
|
||||
if (scope === null && id.isReferencedIdentifier()) {
|
||||
errors.pushErrorDetail(
|
||||
new CompilerErrorDetail({
|
||||
reason: `Encountered a function used before its declaration, which breaks Forget's gating codegen due to hoisting`,
|
||||
|
||||
@@ -663,7 +663,7 @@ const testComplexConfigDefaults: PartialEnvironmentConfig = {
|
||||
source: 'react-compiler-runtime',
|
||||
importSpecifierName: 'shouldInstrument',
|
||||
},
|
||||
globalGating: '__DEV__',
|
||||
globalGating: 'DEV',
|
||||
},
|
||||
enableEmitHookGuards: {
|
||||
source: 'react-compiler-runtime',
|
||||
|
||||
@@ -535,6 +535,30 @@ addObject(BUILTIN_SHAPES, BuiltInRefValueId, [
|
||||
['*', {kind: 'Object', shapeId: BuiltInRefValueId}],
|
||||
]);
|
||||
|
||||
/**
|
||||
* MixedReadOnly =
|
||||
* | primitive
|
||||
* | simple objects (Record<string, MixedReadOnly>)
|
||||
* | Array<MixedReadOnly>
|
||||
*
|
||||
* APIs such as Relay — but also Flux and other data stores — often return a
|
||||
* union of types with some interesting properties in terms of analysis.
|
||||
*
|
||||
* Given this constraint, if data came from Relay, then we should be able to
|
||||
* infer things like `data.items.map(): Array`. That may seem like a leap at
|
||||
* first but remember, we assume you're not patching builtins. Thus the only way
|
||||
* data.items.map can exist and be a function, given the above set of data types
|
||||
* and builtin JS methods, is if `data.items` was an Array, and `data.items.map`
|
||||
* is therefore calling Array.prototype.map. Then we know that function returns
|
||||
* an Array as well. This relies on the fact that map() is being called, so if
|
||||
* data.items was some other type it would error at runtime - so it's sound.
|
||||
*
|
||||
* Note that this shape is currently only used for hook return values, which
|
||||
* means that it's safe to type aliasing method-call return kinds as `Frozen`.
|
||||
*
|
||||
* Also note that all newly created arrays from method-calls (e.g. `.map`)
|
||||
* have the appropriate mutable `BuiltInArray` shape
|
||||
*/
|
||||
addObject(BUILTIN_SHAPES, BuiltInMixedReadonlyId, [
|
||||
[
|
||||
'toString',
|
||||
@@ -546,6 +570,36 @@ addObject(BUILTIN_SHAPES, BuiltInMixedReadonlyId, [
|
||||
returnValueKind: ValueKind.Primitive,
|
||||
}),
|
||||
],
|
||||
[
|
||||
'indexOf',
|
||||
addFunction(BUILTIN_SHAPES, [], {
|
||||
positionalParams: [],
|
||||
restParam: Effect.Read,
|
||||
returnType: {kind: 'Primitive'},
|
||||
calleeEffect: Effect.Read,
|
||||
returnValueKind: ValueKind.Primitive,
|
||||
}),
|
||||
],
|
||||
[
|
||||
'includes',
|
||||
addFunction(BUILTIN_SHAPES, [], {
|
||||
positionalParams: [],
|
||||
restParam: Effect.Read,
|
||||
returnType: {kind: 'Primitive'},
|
||||
calleeEffect: Effect.Read,
|
||||
returnValueKind: ValueKind.Primitive,
|
||||
}),
|
||||
],
|
||||
[
|
||||
'at',
|
||||
addFunction(BUILTIN_SHAPES, [], {
|
||||
positionalParams: [Effect.Read],
|
||||
restParam: null,
|
||||
returnType: {kind: 'Object', shapeId: BuiltInMixedReadonlyId},
|
||||
calleeEffect: Effect.Capture,
|
||||
returnValueKind: ValueKind.Frozen,
|
||||
}),
|
||||
],
|
||||
[
|
||||
'map',
|
||||
addFunction(BUILTIN_SHAPES, [], {
|
||||
@@ -642,9 +696,9 @@ addObject(BUILTIN_SHAPES, BuiltInMixedReadonlyId, [
|
||||
addFunction(BUILTIN_SHAPES, [], {
|
||||
positionalParams: [],
|
||||
restParam: Effect.ConditionallyMutate,
|
||||
returnType: {kind: 'Poly'},
|
||||
returnType: {kind: 'Object', shapeId: BuiltInMixedReadonlyId},
|
||||
calleeEffect: Effect.ConditionallyMutate,
|
||||
returnValueKind: ValueKind.Mutable,
|
||||
returnValueKind: ValueKind.Frozen,
|
||||
noAlias: true,
|
||||
mutableOnlyIfOperandsAreMutable: true,
|
||||
}),
|
||||
|
||||
@@ -1,35 +0,0 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
export default ErrorView;
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
const ErrorView = isForgetEnabled_Fixtures()
|
||||
? (error, _retry) => {
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== error) {
|
||||
t0 = <MessageBox error={error} />;
|
||||
$[0] = error;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
t0 = $[1];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
: (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
export default ErrorView;
|
||||
|
||||
```
|
||||
|
||||
@@ -1,4 +0,0 @@
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
export default ErrorView;
|
||||
@@ -21,7 +21,7 @@ import {
|
||||
import { c as _c } from "react/compiler-runtime"; // @enableEmitFreeze @enableEmitInstrumentForget
|
||||
|
||||
function useFoo(props) {
|
||||
if (__DEV__ && shouldInstrument)
|
||||
if (DEV && shouldInstrument)
|
||||
useRenderCounter("useFoo", "/codegen-emit-imports-same-source.ts");
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
|
||||
@@ -28,7 +28,7 @@ import { c as _c } from "react/compiler-runtime"; // @enableEmitInstrumentForget
|
||||
|
||||
function Bar(props) {
|
||||
"use forget";
|
||||
if (__DEV__ && shouldInstrument)
|
||||
if (DEV && shouldInstrument)
|
||||
useRenderCounter("Bar", "/codegen-instrument-forget-test.ts");
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
@@ -48,7 +48,7 @@ function NoForget(props) {
|
||||
|
||||
function Foo(props) {
|
||||
"use forget";
|
||||
if (__DEV__ && shouldInstrument)
|
||||
if (DEV && shouldInstrument)
|
||||
useRenderCounter("Foo", "/codegen-instrument-forget-test.ts");
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
|
||||
@@ -1,14 +0,0 @@
|
||||
// @gating @compilationMode(annotation)
|
||||
export default function Bar(props) {
|
||||
'use forget';
|
||||
return <div>{props.bar}</div>;
|
||||
}
|
||||
|
||||
function NoForget(props) {
|
||||
return <Bar>{props.noForget}</Bar>;
|
||||
}
|
||||
|
||||
export function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
import {Stringify} from 'shared-runtime';
|
||||
const ErrorView = ({error, _retry}) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default ErrorView;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('ErrorView'),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
import { Stringify } from "shared-runtime";
|
||||
const ErrorView = isForgetEnabled_Fixtures()
|
||||
? (t0) => {
|
||||
const $ = _c(2);
|
||||
const { error } = t0;
|
||||
let t1;
|
||||
if ($[0] !== error) {
|
||||
t1 = <Stringify error={error} />;
|
||||
$[0] = error;
|
||||
$[1] = t1;
|
||||
} else {
|
||||
t1 = $[1];
|
||||
}
|
||||
return t1;
|
||||
}
|
||||
: ({ error, _retry }) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default ErrorView;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("ErrorView"),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>{}</div>
|
||||
@@ -0,0 +1,10 @@
|
||||
// @gating
|
||||
import {Stringify} from 'shared-runtime';
|
||||
const ErrorView = ({error, _retry}) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default ErrorView;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('ErrorView'),
|
||||
params: [{}],
|
||||
};
|
||||
@@ -15,9 +15,22 @@ function NoForget(props) {
|
||||
|
||||
function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
}
|
||||
|
||||
global.DEV = true;
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Foo'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -29,7 +42,7 @@ import { c as _c } from "react/compiler-runtime"; // @enableEmitInstrumentForget
|
||||
const Bar = isForgetEnabled_Fixtures()
|
||||
? function Bar(props) {
|
||||
"use forget";
|
||||
if (__DEV__ && shouldInstrument)
|
||||
if (DEV && shouldInstrument)
|
||||
useRenderCounter("Bar", "/codegen-instrument-forget-gating-test.ts");
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
@@ -53,23 +66,50 @@ function NoForget(props) {
|
||||
const Foo = isForgetEnabled_Fixtures()
|
||||
? function Foo(props) {
|
||||
"use forget";
|
||||
if (__DEV__ && shouldInstrument)
|
||||
if (DEV && shouldInstrument)
|
||||
useRenderCounter("Foo", "/codegen-instrument-forget-gating-test.ts");
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== props.bar) {
|
||||
t0 = <Foo>{props.bar}</Foo>;
|
||||
$[0] = props.bar;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
t0 = $[1];
|
||||
const $ = _c(3);
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return t0;
|
||||
|
||||
const t0 = props.bar - 1;
|
||||
let t1;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t1 = <NoForget />;
|
||||
$[0] = t1;
|
||||
} else {
|
||||
t1 = $[0];
|
||||
}
|
||||
let t2;
|
||||
if ($[1] !== t0) {
|
||||
t2 = <Foo bar={t0}>{t1}</Foo>;
|
||||
$[1] = t0;
|
||||
$[2] = t2;
|
||||
} else {
|
||||
t2 = $[2];
|
||||
}
|
||||
return t2;
|
||||
}
|
||||
: function Foo(props) {
|
||||
"use forget";
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
};
|
||||
|
||||
global.DEV = true;
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Foo"),
|
||||
params: [{ bar: 2 }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div></div>
|
||||
@@ -11,5 +11,18 @@ function NoForget(props) {
|
||||
|
||||
function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
}
|
||||
|
||||
global.DEV = true;
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Foo'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
@@ -0,0 +1,60 @@
|
||||
|
||||
## Input
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
import {identity, useHook as useRenamed} from 'shared-runtime';
|
||||
const _ = {
|
||||
useHook: () => {},
|
||||
};
|
||||
identity(_.useHook);
|
||||
|
||||
function useHook() {
|
||||
useRenamed();
|
||||
return <div>hello world!</div>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: useHook,
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
import { identity, useHook as useRenamed } from "shared-runtime";
|
||||
const _ = {
|
||||
useHook: isForgetEnabled_Fixtures() ? () => {} : () => {},
|
||||
};
|
||||
identity(_.useHook);
|
||||
const useHook = isForgetEnabled_Fixtures()
|
||||
? function useHook() {
|
||||
const $ = _c(1);
|
||||
useRenamed();
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = <div>hello world!</div>;
|
||||
$[0] = t0;
|
||||
} else {
|
||||
t0 = $[0];
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
: function useHook() {
|
||||
useRenamed();
|
||||
return <div>hello world!</div>;
|
||||
};
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: useHook,
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>hello world!</div>
|
||||
@@ -0,0 +1,16 @@
|
||||
// @gating
|
||||
import {identity, useHook as useRenamed} from 'shared-runtime';
|
||||
const _ = {
|
||||
useHook: () => {},
|
||||
};
|
||||
identity(_.useHook);
|
||||
|
||||
function useHook() {
|
||||
useRenamed();
|
||||
return <div>hello world!</div>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: useHook,
|
||||
params: [{}],
|
||||
};
|
||||
@@ -17,6 +17,11 @@ function Foo(props) {
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -66,5 +71,12 @@ const Foo = isForgetEnabled_Fixtures()
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
};
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Bar"),
|
||||
params: [{ bar: 2 }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>2</div>
|
||||
@@ -12,3 +12,8 @@ function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
@@ -12,11 +12,23 @@ function NoForget(props) {
|
||||
return <Bar>{props.noForget}</Bar>;
|
||||
}
|
||||
|
||||
export function Foo(props) {
|
||||
function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -47,25 +59,50 @@ export default Bar;
|
||||
function NoForget(props) {
|
||||
return <Bar>{props.noForget}</Bar>;
|
||||
}
|
||||
|
||||
export const Foo = isForgetEnabled_Fixtures()
|
||||
const Foo = isForgetEnabled_Fixtures()
|
||||
? function Foo(props) {
|
||||
"use forget";
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== props.bar) {
|
||||
t0 = <Foo>{props.bar}</Foo>;
|
||||
$[0] = props.bar;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
t0 = $[1];
|
||||
const $ = _c(3);
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return t0;
|
||||
|
||||
const t0 = props.bar - 1;
|
||||
let t1;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t1 = <NoForget />;
|
||||
$[0] = t1;
|
||||
} else {
|
||||
t1 = $[0];
|
||||
}
|
||||
let t2;
|
||||
if ($[1] !== t0) {
|
||||
t2 = <Foo bar={t0}>{t1}</Foo>;
|
||||
$[1] = t0;
|
||||
$[2] = t2;
|
||||
} else {
|
||||
t2 = $[2];
|
||||
}
|
||||
return t2;
|
||||
}
|
||||
: function Foo(props) {
|
||||
"use forget";
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
};
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Bar"),
|
||||
params: [{ bar: 2 }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>2</div>
|
||||
@@ -0,0 +1,26 @@
|
||||
// @gating @compilationMode(annotation)
|
||||
export default function Bar(props) {
|
||||
'use forget';
|
||||
return <div>{props.bar}</div>;
|
||||
}
|
||||
|
||||
function NoForget(props) {
|
||||
return <Bar>{props.noForget}</Bar>;
|
||||
}
|
||||
|
||||
function Foo(props) {
|
||||
'use forget';
|
||||
if (props.bar < 0) {
|
||||
return props.children;
|
||||
}
|
||||
return (
|
||||
<Foo bar={props.bar - 1}>
|
||||
<NoForget />
|
||||
</Foo>
|
||||
);
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
@@ -17,6 +17,11 @@ export function Foo(props) {
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -66,5 +71,12 @@ export const Foo = isForgetEnabled_Fixtures()
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
};
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Bar"),
|
||||
params: [{ bar: 2 }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>2</div>
|
||||
@@ -12,3 +12,8 @@ export function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
@@ -17,6 +17,11 @@ function Foo(props) {
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -65,5 +70,12 @@ const Foo = isForgetEnabled_Fixtures()
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
};
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Bar"),
|
||||
params: [{ bar: 2 }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>2</div>
|
||||
@@ -12,3 +12,8 @@ function Foo(props) {
|
||||
'use forget';
|
||||
return <Foo>{props.bar}</Foo>;
|
||||
}
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Bar'),
|
||||
params: [{bar: 2}],
|
||||
};
|
||||
@@ -13,6 +13,11 @@ component Component(value: string) {
|
||||
|
||||
export default memo<Props>(Component);
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Component'),
|
||||
params: [{value: 'foo'}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -43,5 +48,12 @@ const Component = isForgetEnabled_Fixtures()
|
||||
|
||||
export default memo<Props>(Component);
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Component"),
|
||||
params: [{ value: "foo" }],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div>foo</div>
|
||||
@@ -8,3 +8,8 @@ component Component(value: string) {
|
||||
}
|
||||
|
||||
export default memo<Props>(Component);
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Component'),
|
||||
params: [{value: 'foo'}],
|
||||
};
|
||||
@@ -35,4 +35,7 @@ export default React.forwardRef(
|
||||
);
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: exception) Fixture not implemented
|
||||
logs: ['forwardRef render functions accept exactly two parameters: props and ref. %s','Did you forget to use the ref parameter?']
|
||||
@@ -3,17 +3,17 @@
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
const Renderer = props => (
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
|
||||
export default Renderer;
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -21,12 +21,14 @@ export default Renderer;
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
import { Stringify } from "shared-runtime";
|
||||
|
||||
const ErrorView = isForgetEnabled_Fixtures()
|
||||
? (error, _retry) => {
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== error) {
|
||||
t0 = <MessageBox error={error} />;
|
||||
t0 = <Stringify error={error} />;
|
||||
$[0] = error;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
@@ -34,9 +36,9 @@ const ErrorView = isForgetEnabled_Fixtures()
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
: (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
: (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
const Renderer = isForgetEnabled_Fixtures()
|
||||
export default isForgetEnabled_Fixtures()
|
||||
? (props) => {
|
||||
const $ = _c(1);
|
||||
let t0;
|
||||
@@ -59,7 +61,8 @@ const Renderer = isForgetEnabled_Fixtures()
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
export default Renderer;
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: exception) Fixture not implemented
|
||||
@@ -0,0 +1,11 @@
|
||||
// @gating
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
@@ -3,15 +3,22 @@
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export const Renderer = props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Renderer'),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -19,12 +26,14 @@ export const Renderer = props => (
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
import { Stringify } from "shared-runtime";
|
||||
|
||||
const ErrorView = isForgetEnabled_Fixtures()
|
||||
? (error, _retry) => {
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== error) {
|
||||
t0 = <MessageBox error={error} />;
|
||||
t0 = <Stringify error={error} />;
|
||||
$[0] = error;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
@@ -32,7 +41,7 @@ const ErrorView = isForgetEnabled_Fixtures()
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
: (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
: (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export const Renderer = isForgetEnabled_Fixtures()
|
||||
? (props) => {
|
||||
@@ -40,10 +49,10 @@ export const Renderer = isForgetEnabled_Fixtures()
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = (
|
||||
<Foo>
|
||||
<Bar />
|
||||
<div>
|
||||
<span />
|
||||
<ErrorView />
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
$[0] = t0;
|
||||
} else {
|
||||
@@ -52,11 +61,17 @@ export const Renderer = isForgetEnabled_Fixtures()
|
||||
return t0;
|
||||
}
|
||||
: (props) => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Renderer"),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div><span></span><div>{"error":{}}</div></div>
|
||||
@@ -0,0 +1,16 @@
|
||||
// @gating
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export const Renderer = props => (
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Renderer'),
|
||||
params: [{}],
|
||||
};
|
||||
@@ -3,15 +3,24 @@
|
||||
|
||||
```javascript
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
export default Renderer = props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
const Renderer = props => (
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
|
||||
export default Renderer;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Renderer'),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
## Code
|
||||
@@ -19,12 +28,14 @@ export default Renderer = props => (
|
||||
```javascript
|
||||
import { isForgetEnabled_Fixtures } from "ReactForgetFeatureFlag";
|
||||
import { c as _c } from "react/compiler-runtime"; // @gating
|
||||
import { Stringify } from "shared-runtime";
|
||||
|
||||
const ErrorView = isForgetEnabled_Fixtures()
|
||||
? (error, _retry) => {
|
||||
const $ = _c(2);
|
||||
let t0;
|
||||
if ($[0] !== error) {
|
||||
t0 = <MessageBox error={error} />;
|
||||
t0 = <Stringify error={error} />;
|
||||
$[0] = error;
|
||||
$[1] = t0;
|
||||
} else {
|
||||
@@ -32,18 +43,18 @@ const ErrorView = isForgetEnabled_Fixtures()
|
||||
}
|
||||
return t0;
|
||||
}
|
||||
: (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
: (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
export default Renderer = isForgetEnabled_Fixtures()
|
||||
const Renderer = isForgetEnabled_Fixtures()
|
||||
? (props) => {
|
||||
const $ = _c(1);
|
||||
let t0;
|
||||
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
||||
t0 = (
|
||||
<Foo>
|
||||
<Bar />
|
||||
<div>
|
||||
<span />
|
||||
<ErrorView />
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
$[0] = t0;
|
||||
} else {
|
||||
@@ -52,11 +63,19 @@ export default Renderer = isForgetEnabled_Fixtures()
|
||||
return t0;
|
||||
}
|
||||
: (props) => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
</div>
|
||||
);
|
||||
export default Renderer;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval("Renderer"),
|
||||
params: [{}],
|
||||
};
|
||||
|
||||
```
|
||||
|
||||
|
||||
### Eval output
|
||||
(kind: ok) <div><span></span><div>{"error":{}}</div></div>
|
||||
@@ -0,0 +1,18 @@
|
||||
// @gating
|
||||
import {Stringify} from 'shared-runtime';
|
||||
|
||||
const ErrorView = (error, _retry) => <Stringify error={error}></Stringify>;
|
||||
|
||||
const Renderer = props => (
|
||||
<div>
|
||||
<span></span>
|
||||
<ErrorView></ErrorView>
|
||||
</div>
|
||||
);
|
||||
|
||||
export default Renderer;
|
||||
|
||||
export const FIXTURE_ENTRYPOINT = {
|
||||
fn: eval('Renderer'),
|
||||
params: [{}],
|
||||
};
|
||||
@@ -1,9 +0,0 @@
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
export default Renderer = props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
@@ -1,9 +0,0 @@
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
export const Renderer = props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
@@ -1,11 +0,0 @@
|
||||
// @gating
|
||||
const ErrorView = (error, _retry) => <MessageBox error={error}></MessageBox>;
|
||||
|
||||
const Renderer = props => (
|
||||
<Foo>
|
||||
<Bar></Bar>
|
||||
<ErrorView></ErrorView>
|
||||
</Foo>
|
||||
);
|
||||
|
||||
export default Renderer;
|
||||
@@ -222,7 +222,6 @@ const skipFilter = new Set([
|
||||
'array-at-mutate-after-capture',
|
||||
'array-join',
|
||||
'array-push-effect',
|
||||
'arrow-function-expr-gating-test',
|
||||
'assignment-in-nested-if',
|
||||
'await-side-effecting-promise',
|
||||
'await',
|
||||
@@ -335,16 +334,10 @@ const skipFilter = new Set([
|
||||
'babel-existing-react-import',
|
||||
'babel-existing-react-kitchensink-import',
|
||||
'call',
|
||||
'codegen-instrument-forget-gating-test',
|
||||
'codegen-instrument-forget-test',
|
||||
'conditional-on-mutable',
|
||||
'constructor',
|
||||
'frozen-after-alias',
|
||||
'gating-test-export-default-function',
|
||||
'gating-test-export-function-and-default',
|
||||
'gating-test-export-function',
|
||||
'gating-test',
|
||||
'gating-with-hoisted-type-reference.flow',
|
||||
'hook-call',
|
||||
'hooks-freeze-arguments',
|
||||
'hooks-freeze-possibly-mutable-arguments',
|
||||
@@ -352,8 +345,6 @@ const skipFilter = new Set([
|
||||
'independent',
|
||||
'interdependent-across-if',
|
||||
'interdependent',
|
||||
'multi-arrow-expr-export-gating-test',
|
||||
'multi-arrow-expr-gating-test',
|
||||
'mutable-liverange-loop',
|
||||
'sequence-expression',
|
||||
'ssa-call-jsx-2',
|
||||
@@ -361,7 +352,6 @@ const skipFilter = new Set([
|
||||
'ssa-newexpression',
|
||||
'ssa-shadowing',
|
||||
'template-literal',
|
||||
'multi-arrow-expr-export-default-gating-test',
|
||||
|
||||
// works, but appears differently when printing
|
||||
// due to optional function argument
|
||||
@@ -407,7 +397,6 @@ const skipFilter = new Set([
|
||||
'infer-functions-hook-with-hook-call',
|
||||
'infer-functions-hook-with-jsx',
|
||||
'infer-function-expression-component',
|
||||
'infer-function-expression-React-memo-gating',
|
||||
'infer-skip-components-without-hooks-or-jsx',
|
||||
'class-component-with-render-helper',
|
||||
'fbt/fbtparam-with-jsx-element-content',
|
||||
@@ -422,7 +411,7 @@ const skipFilter = new Set([
|
||||
'transitive-freeze-function-expressions',
|
||||
|
||||
// nothing to compile/run
|
||||
'repro-no-gating-import-without-compiled-functions',
|
||||
'gating/repro-no-gating-import-without-compiled-functions',
|
||||
|
||||
// TODOs
|
||||
'rules-of-hooks/todo.bail.rules-of-hooks-279ac76f53af',
|
||||
|
||||
Reference in New Issue
Block a user