Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
966a5195ab | ||
|
|
05243074f3 | ||
|
|
056a8e127f |
@@ -127,49 +127,49 @@ All validation passes need to record errors on the environment instead of return
|
||||
|
||||
These passes already accumulate errors internally and return `Result<void, CompilerError>`. The change is: instead of returning the Result, record errors on `env` and return void. Remove the `.unwrap()` call in Pipeline.ts.
|
||||
|
||||
- [x] **4.1 `validateHooksUsage`** (`src/Validation/ValidateHooksUsage.ts`)
|
||||
- [ ] **4.1 `validateHooksUsage`** (`src/Validation/ValidateHooksUsage.ts`)
|
||||
- Change signature from `(fn: HIRFunction): Result<void, CompilerError>` to `(fn: HIRFunction): void`
|
||||
- Record errors on `fn.env` instead of returning `errors.asResult()`
|
||||
- Update Pipeline.ts call site (line 211): remove `.unwrap()`
|
||||
|
||||
- [x] **4.2 `validateNoCapitalizedCalls`** (`src/Validation/ValidateNoCapitalizedCalls.ts`)
|
||||
- [ ] **4.2 `validateNoCapitalizedCalls`** (`src/Validation/ValidateNoCapitalizedCalls.ts`)
|
||||
- Change signature to return void
|
||||
- Fix the hybrid pattern: the direct `CallExpression` path currently throws via `CompilerError.throwInvalidReact()` — change to record on env
|
||||
- The `MethodCall` path already accumulates — change to record on env
|
||||
- Update Pipeline.ts call site (line 214): remove `.unwrap()`
|
||||
|
||||
- [x] **4.3 `validateUseMemo`** (`src/Validation/ValidateUseMemo.ts`)
|
||||
- [ ] **4.3 `validateUseMemo`** (`src/Validation/ValidateUseMemo.ts`)
|
||||
- Change signature to return void
|
||||
- Record hard errors on env instead of returning `errors.asResult()`
|
||||
- The soft `voidMemoErrors` path already uses `env.logErrors()` — keep as-is or also record
|
||||
- Update Pipeline.ts call site (line 170): remove `.unwrap()`
|
||||
|
||||
- [x] **4.4 `dropManualMemoization`** (`src/Inference/DropManualMemoization.ts`)
|
||||
- [ ] **4.4 `dropManualMemoization`** (`src/Inference/DropManualMemoization.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env instead of returning `errors.asResult()`
|
||||
- Update Pipeline.ts call site (line 178): remove `.unwrap()`
|
||||
|
||||
- [x] **4.5 `validateNoRefAccessInRender`** (`src/Validation/ValidateNoRefAccessInRender.ts`)
|
||||
- [ ] **4.5 `validateNoRefAccessInRender`** (`src/Validation/ValidateNoRefAccessInRender.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env instead of returning Result
|
||||
- Update Pipeline.ts call site (line 275): remove `.unwrap()`
|
||||
|
||||
- [x] **4.6 `validateNoSetStateInRender`** (`src/Validation/ValidateNoSetStateInRender.ts`)
|
||||
- [ ] **4.6 `validateNoSetStateInRender`** (`src/Validation/ValidateNoSetStateInRender.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env
|
||||
- Update Pipeline.ts call site (line 279): remove `.unwrap()`
|
||||
|
||||
- [x] **4.7 `validateNoImpureFunctionsInRender`** (`src/Validation/ValidateNoImpureFunctionsInRender.ts`)
|
||||
- [ ] **4.7 `validateNoImpureFunctionsInRender`** (`src/Validation/ValidateNoImpureFunctionsInRender.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env
|
||||
- Update Pipeline.ts call site (line 300): remove `.unwrap()`
|
||||
|
||||
- [x] **4.8 `validateNoFreezingKnownMutableFunctions`** (`src/Validation/ValidateNoFreezingKnownMutableFunctions.ts`)
|
||||
- [ ] **4.8 `validateNoFreezingKnownMutableFunctions`** (`src/Validation/ValidateNoFreezingKnownMutableFunctions.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env
|
||||
- Update Pipeline.ts call site (line 303): remove `.unwrap()`
|
||||
|
||||
- [x] **4.9 `validateExhaustiveDependencies`** (`src/Validation/ValidateExhaustiveDependencies.ts`)
|
||||
- [ ] **4.9 `validateExhaustiveDependencies`** (`src/Validation/ValidateExhaustiveDependencies.ts`)
|
||||
- Change signature to return void
|
||||
- Record errors on env
|
||||
- Update Pipeline.ts call site (line 315): remove `.unwrap()`
|
||||
|
||||
@@ -167,10 +167,14 @@ function runWithEnvironment(
|
||||
env.tryRecord(() => {
|
||||
validateContextVariableLValues(hir);
|
||||
});
|
||||
validateUseMemo(hir);
|
||||
env.tryRecord(() => {
|
||||
validateUseMemo(hir).unwrap();
|
||||
});
|
||||
|
||||
if (env.enableDropManualMemoization) {
|
||||
dropManualMemoization(hir);
|
||||
env.tryRecord(() => {
|
||||
dropManualMemoization(hir).unwrap();
|
||||
});
|
||||
log({kind: 'hir', name: 'DropManualMemoization', value: hir});
|
||||
}
|
||||
|
||||
@@ -215,10 +219,14 @@ function runWithEnvironment(
|
||||
|
||||
if (env.enableValidations) {
|
||||
if (env.config.validateHooksUsage) {
|
||||
validateHooksUsage(hir);
|
||||
env.tryRecord(() => {
|
||||
validateHooksUsage(hir).unwrap();
|
||||
});
|
||||
}
|
||||
if (env.config.validateNoCapitalizedCalls) {
|
||||
validateNoCapitalizedCalls(hir);
|
||||
env.tryRecord(() => {
|
||||
validateNoCapitalizedCalls(hir).unwrap();
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -276,11 +284,15 @@ function runWithEnvironment(
|
||||
}
|
||||
|
||||
if (env.config.validateRefAccessDuringRender) {
|
||||
validateNoRefAccessInRender(hir);
|
||||
env.tryRecord(() => {
|
||||
validateNoRefAccessInRender(hir).unwrap();
|
||||
});
|
||||
}
|
||||
|
||||
if (env.config.validateNoSetStateInRender) {
|
||||
validateNoSetStateInRender(hir);
|
||||
env.tryRecord(() => {
|
||||
validateNoSetStateInRender(hir).unwrap();
|
||||
});
|
||||
}
|
||||
|
||||
if (
|
||||
@@ -303,10 +315,14 @@ function runWithEnvironment(
|
||||
}
|
||||
|
||||
if (env.config.validateNoImpureFunctionsInRender) {
|
||||
validateNoImpureFunctionsInRender(hir);
|
||||
env.tryRecord(() => {
|
||||
validateNoImpureFunctionsInRender(hir).unwrap();
|
||||
});
|
||||
}
|
||||
|
||||
validateNoFreezingKnownMutableFunctions(hir);
|
||||
env.tryRecord(() => {
|
||||
validateNoFreezingKnownMutableFunctions(hir).unwrap();
|
||||
});
|
||||
}
|
||||
|
||||
env.tryRecord(() => {
|
||||
@@ -320,7 +336,9 @@ function runWithEnvironment(
|
||||
env.config.validateExhaustiveEffectDependencies
|
||||
) {
|
||||
// NOTE: this relies on reactivity inference running first
|
||||
validateExhaustiveDependencies(hir);
|
||||
env.tryRecord(() => {
|
||||
validateExhaustiveDependencies(hir).unwrap();
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -724,7 +724,6 @@ function tryCompileFunction(
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Applies React Compiler generated functions to the babel AST by replacing
|
||||
* existing functions in place or inserting new declarations.
|
||||
|
||||
@@ -31,6 +31,7 @@ import {
|
||||
makeInstructionId,
|
||||
} from '../HIR';
|
||||
import {createTemporaryPlace, markInstructionIds} from '../HIR/HIRBuilder';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
type ManualMemoCallee = {
|
||||
kind: 'useMemo' | 'useCallback';
|
||||
@@ -388,7 +389,9 @@ function extractManualMemoizationArgs(
|
||||
* This pass also validates that useMemo callbacks return a value (not void), ensuring that useMemo
|
||||
* is only used for memoizing values and not for running arbitrary side effects.
|
||||
*/
|
||||
export function dropManualMemoization(func: HIRFunction): void {
|
||||
export function dropManualMemoization(
|
||||
func: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const errors = new CompilerError();
|
||||
const isValidationEnabled =
|
||||
func.env.config.validatePreserveExistingMemoizationGuarantees ||
|
||||
@@ -550,9 +553,7 @@ export function dropManualMemoization(func: HIRFunction): void {
|
||||
}
|
||||
}
|
||||
|
||||
if (errors.hasAnyErrors()) {
|
||||
func.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
function findOptionalPlaces(fn: HIRFunction): Set<IdentifierId> {
|
||||
|
||||
@@ -44,6 +44,7 @@ import {
|
||||
eachInstructionValueOperand,
|
||||
eachTerminalOperand,
|
||||
} from '../HIR/visitors';
|
||||
import {Result} from '../Utils/Result';
|
||||
import {retainWhere} from '../Utils/utils';
|
||||
|
||||
const DEBUG = false;
|
||||
@@ -87,7 +88,9 @@ const DEBUG = false;
|
||||
* When we go to compute the dependencies, we then think that the user's manual dep
|
||||
* logic is part of what the memo computation logic.
|
||||
*/
|
||||
export function validateExhaustiveDependencies(fn: HIRFunction): void {
|
||||
export function validateExhaustiveDependencies(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const env = fn.env;
|
||||
const reactive = collectReactiveIdentifiersHIR(fn);
|
||||
|
||||
@@ -214,9 +217,7 @@ export function validateExhaustiveDependencies(fn: HIRFunction): void {
|
||||
},
|
||||
false, // isFunctionExpression
|
||||
);
|
||||
if (error.hasAnyErrors()) {
|
||||
fn.env.recordErrors(error);
|
||||
}
|
||||
return error.asResult();
|
||||
}
|
||||
|
||||
function validateDependencies(
|
||||
|
||||
@@ -26,6 +26,7 @@ import {
|
||||
eachTerminalOperand,
|
||||
} from '../HIR/visitors';
|
||||
import {assertExhaustive} from '../Utils/utils';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
/**
|
||||
* Represents the possible kinds of value which may be stored at a given Place during
|
||||
@@ -87,7 +88,9 @@ function joinKinds(a: Kind, b: Kind): Kind {
|
||||
* may not appear as the callee of a conditional call.
|
||||
* See the note for Kind.PotentialHook for sources of potential hooks
|
||||
*/
|
||||
export function validateHooksUsage(fn: HIRFunction): void {
|
||||
export function validateHooksUsage(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const unconditionalBlocks = computeUnconditionalBlocks(fn);
|
||||
|
||||
const errors = new CompilerError();
|
||||
@@ -423,9 +426,7 @@ export function validateHooksUsage(fn: HIRFunction): void {
|
||||
for (const [, error] of errorsByPlace) {
|
||||
errors.pushErrorDetail(error);
|
||||
}
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
function visitFunctionExpression(errors: CompilerError, fn: HIRFunction): void {
|
||||
|
||||
@@ -5,12 +5,15 @@
|
||||
* LICENSE file in the root directory of this source tree.
|
||||
*/
|
||||
|
||||
import {CompilerError, CompilerErrorDetail, EnvironmentConfig} from '..';
|
||||
import {CompilerError, EnvironmentConfig} from '..';
|
||||
import {ErrorCategory} from '../CompilerError';
|
||||
import {HIRFunction, IdentifierId} from '../HIR';
|
||||
import {DEFAULT_GLOBALS} from '../HIR/Globals';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
export function validateNoCapitalizedCalls(fn: HIRFunction): void {
|
||||
export function validateNoCapitalizedCalls(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const envConfig: EnvironmentConfig = fn.env.config;
|
||||
const ALLOW_LIST = new Set([
|
||||
...DEFAULT_GLOBALS.keys(),
|
||||
@@ -45,16 +48,13 @@ export function validateNoCapitalizedCalls(fn: HIRFunction): void {
|
||||
const calleeIdentifier = value.callee.identifier.id;
|
||||
const calleeName = capitalLoadGlobals.get(calleeIdentifier);
|
||||
if (calleeName != null) {
|
||||
fn.env.recordError(
|
||||
new CompilerErrorDetail({
|
||||
category: ErrorCategory.CapitalizedCalls,
|
||||
reason,
|
||||
description: `${calleeName} may be a component`,
|
||||
loc: value.loc,
|
||||
suggestions: null,
|
||||
}),
|
||||
);
|
||||
continue;
|
||||
CompilerError.throwInvalidReact({
|
||||
category: ErrorCategory.CapitalizedCalls,
|
||||
reason,
|
||||
description: `${calleeName} may be a component`,
|
||||
loc: value.loc,
|
||||
suggestions: null,
|
||||
});
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -85,7 +85,5 @@ export function validateNoCapitalizedCalls(fn: HIRFunction): void {
|
||||
}
|
||||
}
|
||||
}
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
@@ -18,6 +18,7 @@ import {
|
||||
eachTerminalOperand,
|
||||
} from '../HIR/visitors';
|
||||
import {AliasingEffect} from '../Inference/AliasingEffects';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
/**
|
||||
* Validates that functions with known mutations (ie due to types) cannot be passed
|
||||
@@ -42,7 +43,9 @@ import {AliasingEffect} from '../Inference/AliasingEffects';
|
||||
* This pass detects functions with *known* mutations (Store or Mutate, not ConditionallyMutate)
|
||||
* that are passed where a frozen value is expected and rejects them.
|
||||
*/
|
||||
export function validateNoFreezingKnownMutableFunctions(fn: HIRFunction): void {
|
||||
export function validateNoFreezingKnownMutableFunctions(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const errors = new CompilerError();
|
||||
const contextMutationEffects: Map<
|
||||
IdentifierId,
|
||||
@@ -159,7 +162,5 @@ export function validateNoFreezingKnownMutableFunctions(fn: HIRFunction): void {
|
||||
visitOperand(operand);
|
||||
}
|
||||
}
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@ import {CompilerDiagnostic, CompilerError} from '..';
|
||||
import {ErrorCategory} from '../CompilerError';
|
||||
import {HIRFunction} from '../HIR';
|
||||
import {getFunctionCallSignature} from '../Inference/InferMutationAliasingEffects';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
/**
|
||||
* Checks that known-impure functions are not called during render. Examples of invalid functions to
|
||||
@@ -19,7 +20,9 @@ import {getFunctionCallSignature} from '../Inference/InferMutationAliasingEffect
|
||||
* this in several of our validation passes and should unify those analyses into a reusable helper
|
||||
* and use it here.
|
||||
*/
|
||||
export function validateNoImpureFunctionsInRender(fn: HIRFunction): void {
|
||||
export function validateNoImpureFunctionsInRender(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const errors = new CompilerError();
|
||||
for (const [, block] of fn.body.blocks) {
|
||||
for (const instr of block.instructions) {
|
||||
@@ -52,7 +55,5 @@ export function validateNoImpureFunctionsInRender(fn: HIRFunction): void {
|
||||
}
|
||||
}
|
||||
}
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
@@ -27,6 +27,7 @@ import {
|
||||
eachPatternOperand,
|
||||
eachTerminalOperand,
|
||||
} from '../HIR/visitors';
|
||||
import {Err, Ok, Result} from '../Utils/Result';
|
||||
import {retainWhere} from '../Utils/utils';
|
||||
|
||||
/**
|
||||
@@ -119,14 +120,12 @@ class Env {
|
||||
}
|
||||
}
|
||||
|
||||
export function validateNoRefAccessInRender(fn: HIRFunction): void {
|
||||
export function validateNoRefAccessInRender(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const env = new Env();
|
||||
collectTemporariesSidemap(fn, env);
|
||||
const errors = new CompilerError();
|
||||
validateNoRefAccessInRenderImpl(fn, env, errors);
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return validateNoRefAccessInRenderImpl(fn, env).map(_ => undefined);
|
||||
}
|
||||
|
||||
function collectTemporariesSidemap(fn: HIRFunction, env: Env): void {
|
||||
@@ -306,8 +305,7 @@ function joinRefAccessTypes(...types: Array<RefAccessType>): RefAccessType {
|
||||
function validateNoRefAccessInRenderImpl(
|
||||
fn: HIRFunction,
|
||||
env: Env,
|
||||
errors: CompilerError,
|
||||
): RefAccessType {
|
||||
): Result<RefAccessType, CompilerError> {
|
||||
let returnValues: Array<undefined | RefAccessType> = [];
|
||||
let place;
|
||||
for (const param of fn.params) {
|
||||
@@ -338,6 +336,7 @@ function validateNoRefAccessInRenderImpl(
|
||||
env.resetChanged();
|
||||
returnValues = [];
|
||||
const safeBlocks: Array<{block: BlockId; ref: RefId}> = [];
|
||||
const errors = new CompilerError();
|
||||
for (const [, block] of fn.body.blocks) {
|
||||
retainWhere(safeBlocks, entry => entry.block !== block.id);
|
||||
for (const phi of block.phis) {
|
||||
@@ -433,15 +432,13 @@ function validateNoRefAccessInRenderImpl(
|
||||
case 'FunctionExpression': {
|
||||
let returnType: RefAccessType = {kind: 'None'};
|
||||
let readRefEffect = false;
|
||||
const innerErrors = new CompilerError();
|
||||
const result = validateNoRefAccessInRenderImpl(
|
||||
instr.value.loweredFunc.func,
|
||||
env,
|
||||
innerErrors,
|
||||
);
|
||||
if (!innerErrors.hasAnyErrors()) {
|
||||
returnType = result;
|
||||
} else {
|
||||
if (result.isOk()) {
|
||||
returnType = result.unwrap();
|
||||
} else if (result.isErr()) {
|
||||
readRefEffect = true;
|
||||
}
|
||||
env.set(instr.lvalue.identifier.id, {
|
||||
@@ -732,7 +729,7 @@ function validateNoRefAccessInRenderImpl(
|
||||
}
|
||||
|
||||
if (errors.hasAnyErrors()) {
|
||||
return {kind: 'None'};
|
||||
return Err(errors);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -741,8 +738,10 @@ function validateNoRefAccessInRenderImpl(
|
||||
loc: GeneratedSource,
|
||||
});
|
||||
|
||||
return joinRefAccessTypes(
|
||||
...returnValues.filter((env): env is RefAccessType => env !== undefined),
|
||||
return Ok(
|
||||
joinRefAccessTypes(
|
||||
...returnValues.filter((env): env is RefAccessType => env !== undefined),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@@ -13,6 +13,7 @@ import {
|
||||
import {HIRFunction, IdentifierId, isSetStateType} from '../HIR';
|
||||
import {computeUnconditionalBlocks} from '../HIR/ComputeUnconditionalBlocks';
|
||||
import {eachInstructionValueOperand} from '../HIR/visitors';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
/**
|
||||
* Validates that the given function does not have an infinite update loop
|
||||
@@ -42,21 +43,17 @@ import {eachInstructionValueOperand} from '../HIR/visitors';
|
||||
* y();
|
||||
* ```
|
||||
*/
|
||||
export function validateNoSetStateInRender(fn: HIRFunction): void {
|
||||
export function validateNoSetStateInRender(
|
||||
fn: HIRFunction,
|
||||
): Result<void, CompilerError> {
|
||||
const unconditionalSetStateFunctions: Set<IdentifierId> = new Set();
|
||||
const errors = validateNoSetStateInRenderImpl(
|
||||
fn,
|
||||
unconditionalSetStateFunctions,
|
||||
);
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return validateNoSetStateInRenderImpl(fn, unconditionalSetStateFunctions);
|
||||
}
|
||||
|
||||
function validateNoSetStateInRenderImpl(
|
||||
fn: HIRFunction,
|
||||
unconditionalSetStateFunctions: Set<IdentifierId>,
|
||||
): CompilerError {
|
||||
): Result<void, CompilerError> {
|
||||
const unconditionalBlocks = computeUnconditionalBlocks(fn);
|
||||
let activeManualMemoId: number | null = null;
|
||||
const errors = new CompilerError();
|
||||
@@ -95,7 +92,7 @@ function validateNoSetStateInRenderImpl(
|
||||
validateNoSetStateInRenderImpl(
|
||||
instr.value.loweredFunc.func,
|
||||
unconditionalSetStateFunctions,
|
||||
).hasAnyErrors()
|
||||
).isErr()
|
||||
) {
|
||||
// This function expression unconditionally calls a setState
|
||||
unconditionalSetStateFunctions.add(instr.lvalue.identifier.id);
|
||||
@@ -186,5 +183,5 @@ function validateNoSetStateInRenderImpl(
|
||||
}
|
||||
}
|
||||
|
||||
return errors;
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
@@ -20,8 +20,9 @@ import {
|
||||
eachInstructionValueOperand,
|
||||
eachTerminalOperand,
|
||||
} from '../HIR/visitors';
|
||||
import {Result} from '../Utils/Result';
|
||||
|
||||
export function validateUseMemo(fn: HIRFunction): void {
|
||||
export function validateUseMemo(fn: HIRFunction): Result<void, CompilerError> {
|
||||
const errors = new CompilerError();
|
||||
const voidMemoErrors = new CompilerError();
|
||||
const useMemos = new Set<IdentifierId>();
|
||||
@@ -176,9 +177,7 @@ export function validateUseMemo(fn: HIRFunction): void {
|
||||
}
|
||||
}
|
||||
fn.env.logErrors(voidMemoErrors.asResult());
|
||||
if (errors.hasAnyErrors()) {
|
||||
fn.env.recordErrors(errors);
|
||||
}
|
||||
return errors.asResult();
|
||||
}
|
||||
|
||||
function validateNoContextVariableAssignment(
|
||||
|
||||
@@ -14,7 +14,19 @@ function Component() {
|
||||
## Error
|
||||
|
||||
```
|
||||
Found 1 error:
|
||||
Found 2 errors:
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
Expected type for object property 'useHookNotTypedAsHook' from module 'ReactCompilerTest' to be a hook based on the property name.
|
||||
|
||||
error.invalid-type-provider-hook-name-not-typed-as-hook-namespace.ts:4:9
|
||||
2 |
|
||||
3 | function Component() {
|
||||
> 4 | return ReactCompilerTest.useHookNotTypedAsHook();
|
||||
| ^^^^^^^^^^^^^^^^^ Invalid type configuration for module
|
||||
5 | }
|
||||
6 |
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
|
||||
@@ -14,7 +14,19 @@ function Component() {
|
||||
## Error
|
||||
|
||||
```
|
||||
Found 1 error:
|
||||
Found 2 errors:
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
Expected type for object property 'useHookNotTypedAsHook' from module 'ReactCompilerTest' to be a hook based on the property name.
|
||||
|
||||
error.invalid-type-provider-hook-name-not-typed-as-hook.ts:4:9
|
||||
2 |
|
||||
3 | function Component() {
|
||||
> 4 | return useHookNotTypedAsHook();
|
||||
| ^^^^^^^^^^^^^^^^^^^^^ Invalid type configuration for module
|
||||
5 | }
|
||||
6 |
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
|
||||
@@ -14,7 +14,19 @@ function Component() {
|
||||
## Error
|
||||
|
||||
```
|
||||
Found 1 error:
|
||||
Found 2 errors:
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
Expected type for `import ... from 'useDefaultExportNotTypedAsHook'` to be a hook based on the module name.
|
||||
|
||||
error.invalid-type-provider-hooklike-module-default-not-hook.ts:4:15
|
||||
2 |
|
||||
3 | function Component() {
|
||||
> 4 | return <div>{foo()}</div>;
|
||||
| ^^^ Invalid type configuration for module
|
||||
5 | }
|
||||
6 |
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
|
||||
@@ -14,7 +14,19 @@ function Component() {
|
||||
## Error
|
||||
|
||||
```
|
||||
Found 1 error:
|
||||
Found 2 errors:
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
Expected type for object property 'useHookNotTypedAsHook' from module 'ReactCompilerTest' to be a hook based on the property name.
|
||||
|
||||
error.invalid-type-provider-nonhook-name-typed-as-hook.ts:4:15
|
||||
2 |
|
||||
3 | function Component() {
|
||||
> 4 | return <div>{notAhookTypedAsHook()}</div>;
|
||||
| ^^^^^^^^^^^^^^^^^^^ Invalid type configuration for module
|
||||
5 | }
|
||||
6 |
|
||||
|
||||
Error: Invalid type configuration for module
|
||||
|
||||
|
||||
Reference in New Issue
Block a user