logoESLint React
Rules

unsupported-syntax

Validates against syntax that React Compiler does not support.

This rule is currently in rc and only available in v3.0.0 rc releases.

Full Name in eslint-plugin-react-x@rc

react-x/unsupported-syntax

Full Name in @eslint-react/eslint-plugin@rc

@eslint-react/unsupported-syntax

Presets

x recommended recommended-typescript recommended-type-checked strict strict-typescript strict-type-checked

Rule Details

React Compiler needs to statically analyze your code to apply optimizations. Features like eval, with, and immediately-invoked function expressions (IIFEs) in JSX make it impossible or impractical for the compiler to statically understand what the code does at compile time, so the compiler can't optimize components that use them.

This rule checks for the following unsupported patterns:

  • eval — Dynamic code evaluation cannot be statically analyzed.
  • with statements — Dynamically changes scope, preventing static analysis.
  • IIFEs in JSX — Immediately-invoked function expressions within JSX elements or fragments will not be optimized by React Compiler.

Invalid

// ❌ Using eval in component
function Component({ code }) {
  const result = eval(code); // Can't be analyzed
  return <div>{result}</div>;
}
// ❌ Using with statement
function Component() {
  with (Math) { // Changes scope dynamically
    return <div>{sin(PI / 2)}</div>;
  }
}
// ❌ Dynamic property access with eval
function Component({ propName }) {
  const value = eval(`props.${propName}`);
  return <div>{value}</div>;
}
// ❌ IIFE in JSX
function MyComponent() {
  return (
    <SomeJsx>
      {(() => {
        const filteredThings = things.filter(callback);

        if (filteredThings.length === 0) {
          return <Empty />;
        }

        return filteredThings.map((thing) => <Thing key={thing.id} data={thing} />);
      })()}
    </SomeJsx>
  );
}

Valid

// ✅ Use normal property access
function Component({ propName, props }) {
  const value = props[propName]; // Analyzable
  return <div>{value}</div>;
}
// ✅ Use standard Math methods
function Component() {
  return <div>{Math.sin(Math.PI / 2)}</div>;
}
// ✅ eval outside of components and hooks is fine
function notAComponent() {
  const result = eval("1 + 2");
  return result;
}
// ✅ Extract IIFE logic into a variable before JSX
function MyComponent() {
  const thingsList = (() => {
    const filteredThings = things.filter(callback);

    if (filteredThings.length === 0) {
      return <Empty />;
    }

    return filteredThings.map((thing) => <Thing key={thing.id} data={thing} />);
  })();

  return (
    <SomeJsx>
      {thingsList}
    </SomeJsx>
  );
}
// ✅ Use useMemo instead of IIFE
function MyComponent() {
  const thingsList = useMemo(() => {
    const filteredThings = things.filter(callback);

    if (filteredThings.length === 0) {
      return <Empty />;
    }

    return filteredThings.map((thing) => <Thing key={thing.id} data={thing} />);
  }, [things, callback]);

  return (
    <SomeJsx>
      {thingsList}
    </SomeJsx>
  );
}

Troubleshooting

I need to evaluate dynamic code

You might need to evaluate user-provided code:

// ❌ Wrong: eval in component
function Calculator({ expression }) {
  const result = eval(expression); // Unsafe and unoptimizable
  return <div>Result: {result}</div>;
}

Use a safe expression parser instead:

// ✅ Better: Use a safe parser
import { evaluate } from 'mathjs'; // or similar library

function Calculator({ expression }) {
  const [result, setResult] = useState(null);
  const calculate = () => {
    try {
      // Safe mathematical expression evaluation
      setResult(evaluate(expression));
    } catch (error) {
      setResult('Invalid expression');
    }
  };
  return (
    <div>
      <button onClick={calculate}>Calculate</button>
      {result && <div>Result: {result}</div>}
    </div>
  );
}

Note: Never use eval with user input — it's a security risk. Use dedicated parsing libraries for specific use cases like mathematical expressions, JSON parsing, or template evaluation.

I need conditional rendering logic in JSX

You might be using an IIFE in JSX to handle complex conditional rendering:

// ❌ Wrong: IIFE in JSX
function MyComponent() {
  return (
    <div>
      {(() => {
        if (loading) return <Spinner />;
        if (error) return <Error />;
        return <Content />;
      })()}
    </div>
  );
}

Extract the logic into a variable before the return statement, or use a helper component:

// ✅ Better: Extract into a variable
function MyComponent() {
  const content = (() => {
    if (loading) return <Spinner />;
    if (error) return <Error />;
    return <Content />;
  })();

  return <div>{content}</div>;
}
// ✅ Even better: Use ternary or logical expressions
function MyComponent() {
  return (
    <div>
      {loading ? <Spinner /> : error ? <Error /> : <Content />}
    </div>
  );
}

Common Violations

Invalid

function Component({ code }) {
  const result = eval(code);
  //             ^^^ Do not use 'eval' inside components or hooks. 'eval' cannot be statically analyzed and is not supported by React Compiler.
  return <div>{result}</div>;
}
function Component() {
  with (Math) {
  // ^^^ Do not use 'with' statements inside components or hooks. 'with' changes scope dynamically and is not supported by React Compiler.
    return <div>{sin(PI / 2)}</div>;
  }
}
function useMyHook(code) {
  const result = eval(code);
  //             ^^^ Do not use 'eval' inside components or hooks. 'eval' cannot be statically analyzed and is not supported by React Compiler.
  return result;
}
function MyComponent() {
  return (
    <SomeJsx>
      {(() => {
      // ^^^ Avoid using immediately-invoked function expressions in JSX. IIFEs will not be optimized by React Compiler.
        const filteredThings = things.filter(callback);

        if (filteredThings.length === 0) {
          return <Empty />;
        }

        return filteredThings.map((thing) => <Thing key={thing.id} data={thing} />);
      })()}
    </SomeJsx>
  );
}

Valid

function Component({ propName, props }) {
  const value = props[propName];
  return <div>{value}</div>;
}
function Component() {
  return <div>{Math.sin(Math.PI / 2)}</div>;
}
function Component() {
  const handleClick = () => {
    eval("something");
  };
  return <button onClick={handleClick}>Click</button>;
}
function Component() {
  useEffect(() => {
    eval("something");
  }, []);
  return <div>Content</div>;
}
function MyComponent() {
  const thingsList = useMemo(() => {
    const filteredThings = things.filter(callback);

    if (filteredThings.length === 0) {
      return <Empty />;
    }

    return filteredThings.map((thing) => <Thing key={thing.id} data={thing} />);
  }, [things, callback]);

  return (
    <SomeJsx>
      {thingsList}
    </SomeJsx>
  );
}

Resources

Further Reading


See Also

On this page