如何为反应导航 5 开玩笑测试单元创建测试 HoC?

时间:2021-06-03 11:22:48

标签: javascript reactjs react-native jestjs react-navigation

我正在测试这个 HoC 以测试我的 React 导航而不模拟整个导航(用于集成测试):

import React, { memo, ComponentType, cloneElement, ReactNode, isValidElement, useMemo } from 'react'
import { NavigationContainer } from '@react-navigation/native'
import { createStackNavigator, StackNavigationOptions } from '@react-navigation/stack'
import { IdCheckRootStackParamList, IdCheckRoute } from '../types'

interface TestNavigationOptions {
  Stack?: {
    Navigator: ComponentType,
    Screen: ComponentType,
  }
  initialRouteName?: string
  initialRouteOptions: Record<string, unknown>
  routes?: Array<IdCheckRoute<Record<string, unknown>, IdCheckRootStackParamList>>
  screenOptions?: StackNavigationOptions
}

const defaultOptions = {
  Stack: createStackNavigator(),
  initialRouteName: 'Home',
  initialRouteOptions: undefined,
  routes: undefined,
  screenOptions: undefined
}

export const withTestNavigation = (HomeComponent?: ComponentType | ReactNode, options?: TestNavigationOptions) => {
  const {
    Stack,
    initialRouteName,
    initialRouteOptions,
    routes,
    screenOptions,
  } =  { ...defaultOptions, ...options }
  const ComponentWithTestNavigation = memo(function TestNavigation() {
    const Home = useMemo(() => isValidElement(HomeComponent) ? (props = {}) => cloneElement(HomeComponent, props) : HomeComponent, [])
    return (
      <NavigationContainer>
        <Stack.Navigator
          initialRouteName={initialRouteName}
          screenOptions={screenOptions}
        >
          {Home && (
            <Stack.Screen
              name={initialRouteName}
              component={Home as ComponentType}
              options={initialRouteOptions}
            />
          )}
          {routes?.map((route) => (
            <Stack.Screen
              key={route.name}
              name={route.name}
              component={route.component}
              options={route.options}
            />
          ))}
        </Stack.Navigator>
      </NavigationContainer>
    )
  })
  return <ComponentWithTestNavigation />
}

Snippet

我的测试如下所示:

const { toJSON } = render(withTestNavigation(<Validation />))
expect(toJSON()).not.toBe(null)

我希望渲染,相反,我有 null

我确实按照 react-navigation 5 中的说明为 jest 配置了 mock,并且我确实使用了 @react-navigation/native@react-navigation/stack 的最新发布版本。

你们知道为什么我的测试中总是 render(withTestNavigation(TestComponent)).toJSON()null 吗?

0 个答案:

没有答案