From 049b17a580bcff373f59882d2cec828c1f781319 Mon Sep 17 00:00:00 2001 From: M-i-k-e-l Date: Thu, 1 Jan 2026 13:00:34 +0200 Subject: [PATCH 1/2] Fix (most) typescript issue --- package.json | 2 +- packages/react-native-ui-lib/package.json | 2 +- .../src/components/featureHighlight/index.tsx | 2 -- .../src/components/hint/HintMockChildren.tsx | 2 +- .../src/components/hint/HintOld.tsx | 2 +- .../src/components/image/index.tsx | 14 +++++++---- .../src/components/scrollBar/index.tsx | 23 ++++++++++++++----- .../src/components/view/index.tsx | 3 +-- .../src/hooks/useCombinedRefs/index.ts | 1 - .../src/typings/module.d.ts | 15 +++++++++--- yarn.lock | 15 ++++++------ 11 files changed, 51 insertions(+), 30 deletions(-) diff --git a/package.json b/package.json index dd3b870cf1..663622fdfa 100644 --- a/package.json +++ b/package.json @@ -43,7 +43,7 @@ "@testing-library/react-hooks": "^8.0.1", "@testing-library/react-native": "^11.5.1", "@topcli/spinner": "patch:@topcli/spinner@npm%3A2.1.2#./.yarn/patches/@topcli-spinner-npm-2.1.2-262b584167.patch", - "@types/hoist-non-react-statics": "^3.3.1", + "@types/hoist-non-react-statics": "^3.3.7", "@types/jest": "^29.5.13", "@types/lodash": "^4.0.0", "@types/react": "19.0.0", diff --git a/packages/react-native-ui-lib/package.json b/packages/react-native-ui-lib/package.json index 3e7deda6fb..35dfa5d830 100644 --- a/packages/react-native-ui-lib/package.json +++ b/packages/react-native-ui-lib/package.json @@ -66,7 +66,7 @@ "@shopify/flash-list": "1.7.6", "@testing-library/react-hooks": "^8.0.1", "@testing-library/react-native": "^11.5.1", - "@types/hoist-non-react-statics": "^3.3.1", + "@types/hoist-non-react-statics": "^3.3.7", "@types/jest": "^29.5.13", "@types/lodash": "^4.0.0", "@types/react": "19.0.0", diff --git a/packages/react-native-ui-lib/src/components/featureHighlight/index.tsx b/packages/react-native-ui-lib/src/components/featureHighlight/index.tsx index 229597a5b5..fdde33b55f 100644 --- a/packages/react-native-ui-lib/src/components/featureHighlight/index.tsx +++ b/packages/react-native-ui-lib/src/components/featureHighlight/index.tsx @@ -327,7 +327,6 @@ class FeatureHighlight extends Component { titleStyle ]} numberOfLines={titleNumberOfLines} - // @ts-expect-error pointerEvents={'none'} > {title} @@ -338,7 +337,6 @@ class FeatureHighlight extends Component { text70 style={[styles.message, {color}, messageStyle]} numberOfLines={messageNumberOfLines} - // @ts-expect-error pointerEvents={'none'} > {message} diff --git a/packages/react-native-ui-lib/src/components/hint/HintMockChildren.tsx b/packages/react-native-ui-lib/src/components/hint/HintMockChildren.tsx index 8bf9607fc4..92f29d09a8 100644 --- a/packages/react-native-ui-lib/src/components/hint/HintMockChildren.tsx +++ b/packages/react-native-ui-lib/src/components/hint/HintMockChildren.tsx @@ -25,7 +25,7 @@ export default function HintMockChildren({children, backdropColor, targetLayout} {React.cloneElement(children, { collapsable: false, key: 'mock', - style: [children.props.style, styles.mockChildren] + style: [(children.props as any).style, styles.mockChildren] })} ); diff --git a/packages/react-native-ui-lib/src/components/hint/HintOld.tsx b/packages/react-native-ui-lib/src/components/hint/HintOld.tsx index 1371c87199..ecc68838fc 100644 --- a/packages/react-native-ui-lib/src/components/hint/HintOld.tsx +++ b/packages/react-native-ui-lib/src/components/hint/HintOld.tsx @@ -593,7 +593,7 @@ class Hint extends Component { {React.cloneElement(children, { collapsable: false, key: 'mock', - style: [children.props.style, styles.mockChildren] + style: [(children.props as any).style, styles.mockChildren] })} ); diff --git a/packages/react-native-ui-lib/src/components/image/index.tsx b/packages/react-native-ui-lib/src/components/image/index.tsx index 3057023875..09bc8fa76f 100644 --- a/packages/react-native-ui-lib/src/components/image/index.tsx +++ b/packages/react-native-ui-lib/src/components/image/index.tsx @@ -245,17 +245,21 @@ class Image extends PureComponent { const {margins} = modifiers; return ( - // @ts-ignore { - /** - * Whether to use a FlatList. NOTE: you must pass 'data' and 'renderItem' props as well - */ - useList?: boolean; +export type ListProps = + | (FlatListProps & { + /** + * Whether to use a FlatList. NOTE: you must pass 'data' and 'renderItem' props as well + */ + useList: true; + }) + | (ScrollViewProps & { + /** + * Whether to use a ScrollView. NOTE: you must pass 'contentContainerStyle' prop as well + */ + useList?: false; + }); + +export type ScrollBarProps = ListProps & { /** * The element to use as a container, instead of a View */ @@ -58,7 +69,7 @@ export interface ScrollBarProps extends FlatListProps { * The index to currently focus on */ focusIndex?: number; -} +}; type Props = ScrollBarProps & ForwardRefInjectedProps; diff --git a/packages/react-native-ui-lib/src/components/view/index.tsx b/packages/react-native-ui-lib/src/components/view/index.tsx index b082ea2ea4..f223cd09fd 100644 --- a/packages/react-native-ui-lib/src/components/view/index.tsx +++ b/packages/react-native-ui-lib/src/components/view/index.tsx @@ -116,7 +116,7 @@ function View(props: ViewProps, ref: any) { } return container; - }, [useSafeArea, animated, reanimated]); + }, [useSafeArea, animated, reanimated]) as React.ComponentType; const _style = useMemo(() => { const backgroundColor = backgroundColorProps || backgroundColorModifiers; @@ -155,7 +155,6 @@ function View(props: ViewProps, ref: any) { } return ( - //@ts-expect-error (...refs: React.Ref[]) => { if (typeof ref === 'function') { ref(targetRef.current); } else { - // @ts-expect-error ref.current = targetRef.current; } }); diff --git a/packages/react-native-ui-lib/src/typings/module.d.ts b/packages/react-native-ui-lib/src/typings/module.d.ts index 56aa60b906..7f0f87496c 100644 --- a/packages/react-native-ui-lib/src/typings/module.d.ts +++ b/packages/react-native-ui-lib/src/typings/module.d.ts @@ -3,11 +3,20 @@ declare namespace globalThis { var _UILIB_TESTING: boolean; } +declare global { + // eslint-disable-next-line no-var + var _UILIB_TESTING: boolean; +} + // This support importing png files, typing wise declare module '*.png'; -declare namespace JSX { - interface IntrinsicAttributes { - fsTagName?: string; +import 'react'; + +declare module 'react' { + namespace JSX { + interface IntrinsicAttributes { + fsTagName?: string; + } } } diff --git a/yarn.lock b/yarn.lock index 47ce15a578..838b5d9d99 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2986,13 +2986,14 @@ __metadata: languageName: node linkType: hard -"@types/hoist-non-react-statics@npm:^3.3.1": - version: 3.3.5 - resolution: "@types/hoist-non-react-statics@npm:3.3.5" +"@types/hoist-non-react-statics@npm:^3.3.7": + version: 3.3.7 + resolution: "@types/hoist-non-react-statics@npm:3.3.7" dependencies: - "@types/react": "npm:*" hoist-non-react-statics: "npm:^3.3.0" - checksum: 10c0/2a3b64bf3d9817d7830afa60ee314493c475fb09570a64e7737084cd482d2177ebdddf888ce837350bac51741278b077683facc9541f052d4bbe8487b4e3e618 + peerDependencies: + "@types/react": "*" + checksum: 10c0/ed8f4e88338f7d021d0f956adf6089d2a12b2e254a03c05292324f2e986d2376eb9efdb8a4f04596823e8fca88c9d06361d20dab4a2a00dc935fb36ac911de55 languageName: node linkType: hard @@ -9646,7 +9647,7 @@ __metadata: "@testing-library/react-hooks": "npm:^8.0.1" "@testing-library/react-native": "npm:^11.5.1" "@topcli/spinner": "patch:@topcli/spinner@npm%3A2.1.2#./.yarn/patches/@topcli-spinner-npm-2.1.2-262b584167.patch" - "@types/hoist-non-react-statics": "npm:^3.3.1" + "@types/hoist-non-react-statics": "npm:^3.3.7" "@types/jest": "npm:^29.5.13" "@types/lodash": "npm:^4.0.0" "@types/react": "npm:19.0.0" @@ -9697,7 +9698,7 @@ __metadata: "@shopify/flash-list": "npm:1.7.6" "@testing-library/react-hooks": "npm:^8.0.1" "@testing-library/react-native": "npm:^11.5.1" - "@types/hoist-non-react-statics": "npm:^3.3.1" + "@types/hoist-non-react-statics": "npm:^3.3.7" "@types/jest": "npm:^29.5.13" "@types/lodash": "npm:^4.0.0" "@types/react": "npm:19.0.0" From e1b5902835425cacd3b308366cf29af2219a6422 Mon Sep 17 00:00:00 2001 From: Miki Leib <38354019+M-i-k-e-l@users.noreply.github.com> Date: Wed, 7 Jan 2026 09:32:56 +0200 Subject: [PATCH 2/2] Infra/v9 tests (#3903) * Fix button and update @testing-library/react-native version * Remove unsupported modifiers methods, add docs and fix tests The old TextField was the only usage of the removed methods and it was only used by MaskedInput which is deprecated --- docs/getting-started/v8.md | 3 +- docs/getting-started/v9.md | 21 + package.json | 5 +- packages/react-native-ui-lib/package.json | 2 +- .../src/commons/__tests__/modifiers.spec.js | 36 - .../src/commons/baseComponent.tsx | 2 - .../src/commons/modifiers.ts | 21 - .../components/button/__tests__/index.spec.js | 118 ++- .../__tests__/maskedInput.old.spec.tsx | 20 - ...nput.new.spec.tsx => maskedInput.spec.tsx} | 4 +- .../src/components/maskedInput/index.tsx | 137 +++- .../maskedInput/maskedInput.api.json | 1 - .../src/components/maskedInput/new.tsx | 129 ---- .../src/components/maskedInput/old.js | 82 -- .../src/components/numberInput/index.tsx | 2 +- .../picker/__tests__/index.spec.tsx | 12 +- .../src/components/picker/types.ts | 1 - .../src/components/textFieldOld/index.tsx | 711 ------------------ yarn.lock | 120 ++- 19 files changed, 322 insertions(+), 1105 deletions(-) create mode 100644 docs/getting-started/v9.md delete mode 100644 packages/react-native-ui-lib/src/components/maskedInput/__tests__/maskedInput.old.spec.tsx rename packages/react-native-ui-lib/src/components/maskedInput/__tests__/{maskedInput.new.spec.tsx => maskedInput.spec.tsx} (87%) delete mode 100644 packages/react-native-ui-lib/src/components/maskedInput/new.tsx delete mode 100644 packages/react-native-ui-lib/src/components/maskedInput/old.js delete mode 100644 packages/react-native-ui-lib/src/components/textFieldOld/index.tsx diff --git a/docs/getting-started/v8.md b/docs/getting-started/v8.md index 1a29754cd7..820d60455f 100644 --- a/docs/getting-started/v8.md +++ b/docs/getting-started/v8.md @@ -1,5 +1,5 @@ --- -sidebar_position: 5 +sidebar_position: 6 sidebar_label: Migrating v7 -> v8 title: "Migrating v7 -> v8" # path: "/getting-started/v8" @@ -7,6 +7,7 @@ title: "Migrating v7 -> v8" ## `react-native-ui-lib@8.x.x` ## General +Now supports react-native 0.77 `uilib-native` (our native library) has been moved from `dependencies` to `peerDependencies`. Make sure to `pod install` after updating. We do plan on making this optional in the future. diff --git a/docs/getting-started/v9.md b/docs/getting-started/v9.md new file mode 100644 index 0000000000..31dcbda645 --- /dev/null +++ b/docs/getting-started/v9.md @@ -0,0 +1,21 @@ +--- +sidebar_position: 7 +sidebar_label: Migrating v8 -> v9 +title: "Migrating v8 -> v9" +# path: "/getting-started/v9" +--- +## `react-native-ui-lib@9.x.x` + +## General +Now supports react-native 0.78 and React 19 + +## Components + +### MaskedInput +Only the newer version is now available (the `migrate` prop is removed) + +## Utils + +### modifiers +extractOwnProps - removed +extractComponentProps - removed diff --git a/package.json b/package.json index db5af76fbd..afa75f8de9 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,8 @@ "ios": "yarn workspace react-native-ui-lib ios", "android": "yarn workspace react-native-ui-lib android", "iPad": "yarn workspace react-native-ui-lib iPad", - "test": "yarn lint && yarn workspace react-native-ui-lib test", + "test": "yarn workspace react-native-ui-lib test", + "pretest": "yarn lint", "lint": "eslint packages -c .eslintrc.js --ext .tsx,.ts,.js", "lint:fix": "eslint packages -c .eslintrc.js --fix", "build:dev": "tsc --p tsconfig.dev.json", @@ -40,7 +41,7 @@ "@react-native/metro-config": "0.78.3", "@react-native/typescript-config": "0.78.3", "@shopify/flash-list": "1.7.6", - "@testing-library/react-native": "^11.5.1", + "@testing-library/react-native": "^13.3.3", "@types/hoist-non-react-statics": "^3.3.7", "@types/jest": "^29.5.13", "@types/lodash": "^4.0.0", diff --git a/packages/react-native-ui-lib/package.json b/packages/react-native-ui-lib/package.json index 56652a5e46..462e5cb44c 100644 --- a/packages/react-native-ui-lib/package.json +++ b/packages/react-native-ui-lib/package.json @@ -64,7 +64,7 @@ "@react-native/metro-config": "0.78.3", "@react-native/typescript-config": "0.78.3", "@shopify/flash-list": "1.7.6", - "@testing-library/react-native": "^11.5.1", + "@testing-library/react-native": "^13.3.3", "@types/hoist-non-react-statics": "^3.3.7", "@types/jest": "^29.5.13", "@types/lodash": "^4.0.0", diff --git a/packages/react-native-ui-lib/src/commons/__tests__/modifiers.spec.js b/packages/react-native-ui-lib/src/commons/__tests__/modifiers.spec.js index 789bf2d07d..310a601b27 100644 --- a/packages/react-native-ui-lib/src/commons/__tests__/modifiers.spec.js +++ b/packages/react-native-ui-lib/src/commons/__tests__/modifiers.spec.js @@ -282,24 +282,6 @@ describe('Modifiers', () => { }); }); - // describe('extractOwnProps', () => { - // it('should extract the component props from a props object', () => { - // const props = {color: 'red', topShadow: 1, bottomShadow: 2}; - // expect(MultipleShadow.extractOwnProps(props)).toEqual({ - // topShadow: 1, - // bottomShadow: 2, - // }); - // }); - - // it('should omit props that were required to ignore', () => { - // const props = {color: 'red', topShadow: 1, bottomShadow: 2}; - // expect(MultipleShadow.extractOwnProps(props, 'topShadow')).toEqual({ - // bottomShadow: 2, - // }); - // expect(MultipleShadow.extractOwnProps(props, ['topShadow', 'bottomShadow'])).toEqual({}); - // }); - // }); - describe('extractModifiersProps', () => { it('should return all modifiers props', () => { expect(uut.extractModifierProps({ @@ -343,24 +325,6 @@ describe('Modifiers', () => { }); }); - describe('extractOwnProps', () => { - it('should extract the component props from a props object', () => { - const props = {color: 'red', prop1: 'text', prop2: 2}; - expect(uut.extractOwnProps.bind(SampleComponent)(props)).toEqual({ - prop1: 'text', - prop2: 2 - }); - }); - - it('should omit props that were required to ignore', () => { - const props = {color: 'red', prop1: 'text', prop2: 2}; - expect(uut.extractOwnProps.bind(SampleComponent)(props, 'prop1')).toEqual({ - prop2: 2 - }); - expect(uut.extractOwnProps.bind(SampleComponent)(props, ['prop1', 'prop2'])).toEqual({}); - }); - }); - describe('getThemeProps', () => { beforeEach(() => { ThemeManager.setComponentTheme('SampleComponent', undefined); diff --git a/packages/react-native-ui-lib/src/commons/baseComponent.tsx b/packages/react-native-ui-lib/src/commons/baseComponent.tsx index 2ab4affa83..73bdad4672 100644 --- a/packages/react-native-ui-lib/src/commons/baseComponent.tsx +++ b/packages/react-native-ui-lib/src/commons/baseComponent.tsx @@ -10,8 +10,6 @@ export default function baseComponent(usePure: boolean): ComponentType { styles: any; view: any; - static extractOwnProps = Modifiers.extractOwnProps; - constructor(props: any) { super(props); if (!this.styles) { diff --git a/packages/react-native-ui-lib/src/commons/modifiers.ts b/packages/react-native-ui-lib/src/commons/modifiers.ts index 1815b21305..7117654191 100644 --- a/packages/react-native-ui-lib/src/commons/modifiers.ts +++ b/packages/react-native-ui-lib/src/commons/modifiers.ts @@ -338,27 +338,6 @@ export function extractModifierProps(props: Dictionary) { return modifierProps; } -/** - * TODO: - * @deprecated switch to Modifiers#extractComponentProps - */ -export function extractOwnProps(props: Dictionary, ignoreProps: string[]) { - //@ts-ignore - const ownPropTypes = this.propTypes; - const ownProps = _.flow((props: Dictionary) => _.pickBy(props, (_value, key) => _.includes(Object.keys(ownPropTypes), key)), - props => _.omit(props, ignoreProps))(props); - - return ownProps; -} - -export function extractComponentProps(component: any, props: Dictionary, ignoreProps: string[] = []) { - const componentPropTypes = component.propTypes; - const componentProps = _.flow((props: Dictionary) => _.pickBy(props, (_value, key) => _.includes(Object.keys(componentPropTypes), key)), - props => _.omit(props, ignoreProps))(props); - - return componentProps; -} - export function getComponentName(componentDisplayName: string) { //@ts-ignore return componentDisplayName || this.displayName || this.constructor.displayName || this.constructor.name; diff --git a/packages/react-native-ui-lib/src/components/button/__tests__/index.spec.js b/packages/react-native-ui-lib/src/components/button/__tests__/index.spec.js index 722978bfa2..61b6820f48 100644 --- a/packages/react-native-ui-lib/src/components/button/__tests__/index.spec.js +++ b/packages/react-native-ui-lib/src/components/button/__tests__/index.spec.js @@ -1,5 +1,5 @@ import React from 'react'; -import renderer from 'react-test-renderer'; +import {render} from '@testing-library/react-native'; import Button from '../index'; import View from '../../view'; import {Colors, ThemeManager} from '../../../style'; @@ -12,54 +12,54 @@ describe('Button', () => { }); it('should render default button', () => { - const tree = renderer.create(