Skip to content

Commit

Permalink
fix: isFragment not support React 19 (#604)
Browse files Browse the repository at this point in the history
  • Loading branch information
zombieJ authored Dec 12, 2024
1 parent 161915b commit a78b20c
Show file tree
Hide file tree
Showing 4 changed files with 79 additions and 2 deletions.
2 changes: 1 addition & 1 deletion src/Children/toArray.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import isFragment from '../React/isFragment';
import React from 'react';
import { isFragment } from 'react-is';

export interface Option {
keepEmpty?: boolean;
Expand Down
19 changes: 19 additions & 0 deletions src/React/isFragment.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const REACT_ELEMENT_TYPE_18 = Symbol.for('react.element');
const REACT_ELEMENT_TYPE_19 = Symbol.for('react.transitional.element');
const REACT_FRAGMENT_TYPE = Symbol.for('react.fragment');

/**
* Compatible with React 18 or 19 to check if node is a Fragment.
*/
export default function isFragment(object: any) {
return (
// Base object type
object &&
typeof object === 'object' &&
// React Element type
(object.$$typeof === REACT_ELEMENT_TYPE_18 ||
object.$$typeof === REACT_ELEMENT_TYPE_19) &&
// React Fragment type
object.type === REACT_FRAGMENT_TYPE
);
}
3 changes: 2 additions & 1 deletion src/ref.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import type * as React from 'react';
import { isValidElement } from 'react';
import { ForwardRef, isFragment, isMemo } from 'react-is';
import { ForwardRef, isMemo } from 'react-is';
import useMemo from './hooks/useMemo';
import isFragment from './React/isFragment';

export const fillRef = <T>(ref: React.Ref<T>, node: T) => {
if (typeof ref === 'function') {
Expand Down
57 changes: 57 additions & 0 deletions tests/toArray-19.test.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
import React from 'react';
import { render } from '@testing-library/react';
import toArray from '../src/Children/toArray';

jest.mock('react', () => {
const react19 = jest.requireActual('react-19');
return react19;
});

jest.mock('react-dom', () => {
const reactDom19 = jest.requireActual('react-dom-19');
return reactDom19;
});

jest.mock('react-dom/client', () => {
const reactDom19Client = jest.requireActual('react-dom-19/client');
return reactDom19Client;
});

jest.mock('react-dom/test-utils', () => {
const reactDom19Test = jest.requireActual('react-dom-19/test-utils');
return reactDom19Test;
});

class UL extends React.Component<{
children?: React.ReactNode;
}> {
render() {
return <ul>{this.props.children}</ul>;
}
}

describe('toArray', () => {
it('Fragment', () => {
const ulRef = React.createRef<UL>();

render(
<UL ref={ulRef}>
<li key="1">1</li>
<>
<li key="2">2</li>
<li key="3">3</li>
</>
<React.Fragment>
<>
<li key="4">4</li>
<li key="5">5</li>
</>
</React.Fragment>
</UL>,
);

const children = toArray(ulRef.current.props.children);
expect(children).toHaveLength(5);
expect(children.map(c => c.key)).toEqual(['1', '2', '3', '4', '5']);
});
});

0 comments on commit a78b20c

Please sign in to comment.