专门针对React Native的平台测试

时间:2019-03-06 12:24:22

标签: react-native jestjs

我正在研究的RN项目旨在作为“仅限Android”使用,因此无需添加带有cocoapods之类的“ react-native-firebase”库。我必须事先提到,我无权访问任何mac或macbook。 这是package.json的片段

...
"scripts": {
  "test": "jest"
},
"jest": {
  "preset": "react-native"
},
...

和babel.config.js

module.exports = {
    presets: [
      [
        'module:metro-react-native-babel-preset',
        {
          targets: {
            node: 'current',
          },
          loose: true,
          modules: 'auto',
        },
      ],
    ],
  };

用于笑话测试的虚拟功能:

// testing jest
const generateText = (name, age) => {
  return `${name} (${age} years old)`;
};

并对其进行单元测试:

import { generateText } from '../actions/authActions';

test('Some test', () => {
  const text = generateText('Zuul', 300);
  expect(text).toBe('Zuul (300 years old)');
});

在运行所有yarn test的所有设置的情况下,将给出以下输出:

    RNFirebase core module was not found natively on iOS,
ensure you have correctly included the RNFirebase pod in
your projects `Podfile` and have run `pod install`.

问题是,有没有办法使玩笑跳过与ios相关的检查,而只专注于android的东西?

更新: 显然,有一种方法可以覆盖开玩笑的预设,所以我将其添加到package.json:

"jest": {
  "preset": "react-native",
  "haste": {
    "defaultPlatform": "android",
    "platforms": [
      "android",
      "ios",
      "native"
    ],
    "providesModuleNodeModules": [
      "react-native"
    ]
  }
},

现在我收到此错误消息:

RNFirebase core module was not found natively on Android,
ensure you have correctly added the RNFirebase and Firebase
gradle dependencies to your `android/app/build.gradle` file.

根本不是这种情况,因为所有必需的依赖项都已添加到build.gradle:

dependencies {
    ...
    implementation project(':react-native-firebase')
    // Firebase dependencies
    implementation "com.google.android.gms:play-services-base:16.0.1"
    implementation "com.google.firebase:firebase-core:16.0.6"
    implementation('com.crashlytics.sdk.android:crashlytics:2.9.5@aar') {
        transitive = true
    }
    implementation "com.google.firebase:firebase-messaging:17.3.4"
    implementation 'me.leolin:ShortcutBadger:1.1.21@aar'
    ...
}

1 个答案:

答案 0 :(得分:1)

显然,这是一个众所周知的问题。我找到了解决方法here。 基本上,我将jest设置从package.json移到了jest.config.js:

//jest.config.js
module.exports = {
  preset: 'react-native',
  haste: {
    defaultPlatform: 'android',
    platforms: [
      'android',
      'ios',
      'native',
    ],
    providesModuleNodeModules: [
      'react-native',
    ],
  },
  setupFilesAfterEnv: ['./src/__mocks__/mockNativeLibs.js'],
  automock: false,
  moduleNameMapper: {
    '\\.(css|less)$': 'identity-obj-proxy',
    '^.+\\.(jpg|jpeg|gif|png|mp4|mkv|avi|webm|swf|wav|mid)$': 'jest-static-stubs/$1',
  },
  globals: {
    __DEV__: true,
  },
  collectCoverageFrom: [
    '**/src/**/*.{js,jsx}',
    '!**/src/**/style.js',
    '!**/src/**/index.js',
    '!**/src/theme/**',
    '!**/android/**',
    '!**/ios/**',
    '!**/node_modules/**',
    '!**/scripts/**',
    '!**/__test__/**',
  ],
  verbose: true,
  testPathIgnorePatterns: ['/node_modules/'],
};

并添加了此文件:

//mockNativeLibs.js
jest.mock('react-native-firebase', () => {
  return {
    messaging: jest.fn(() => {
      return {
        hasPermission: jest.fn(() => Promise.resolve(true)),
        subscribeToTopic: jest.fn(),
        unsubscribeFromTopic: jest.fn(),
        requestPermission: jest.fn(() => Promise.resolve(true)),
        getToken: jest.fn(() => Promise.resolve('myMockToken')),
      };
    }),
    notifications: jest.fn(() => {
      return {
        onNotification: jest.fn(),
        onNotificationDisplayed: jest.fn(),
      };
    }),
    crashlytics: jest.fn(() => {
      return {
        recordError: jest.fn(),
      };
    }),
  };
});

// apparently there were more libraries causing problems with jest
jest.mock('pushy-react-native', () => {
  return {};
});

jest.mock('react-native-localize', () => {
  return {};
});

jest.mock('react-native-sound', () => {
  return {};
});