Blog

Developing an Alexa Skill, locally

At Ensolvers, we try to write as many automated test cases we can, in different layers of the software products we build, since it helps auto-documenting the code, ensure software quality and eases maintenance.

In our several React Native projects, we use Detox, a testing and automation library. Detox allows simulating user behaviour like taps, swipe, scroll, etc. in particular components and then assert for results – for instance, UI transformations. In this way, it is possible to replicate a full use-case flow in the application to test it from end to end.

Step1: InstallationInstalling detox in an existing project is pretty simple

  • Install Detox
  • npm install detox –save-dev
  • Install a test runner, you can choose Jest or Mocha (in my case was Jest):npm install jest –save-dev
  1. Set up test-code scaffolds (automated)

detox init -r jest

this will create a e2e folder with config files and a first test.

  1. Configuration
  • IOS

Add detox configuration to packaje.json:

“detox”: {

“configurations”: {

“ios.sim.debug”: {

“binaryPath”: “ios/build/Build/Products/Debug-iphonesimulator/example.app”,

“build”: “xcodebuild -project ios/example.xcodeproj -scheme example -configuration Debug -sdk iphonesimulator -derivedDataPath ios/build”,

“type”: “ios.simulator”,

“device”: {

“type”: “iPhone 11 Pro”

}

}

}

}

  • Android
    1. Set sdk root adding following line to bashrc:

export ANDROID_SDK_ROOT=$HOME/Android/Sdk

  1. Add Detox dependency to your root buildscript (i.e. android/build.gradle):

// Note: add the ‘allproject’ section if it doesn’t exist

allprojects {

repositories {

// …

google()

maven {

// All of Detox’ artifacts are provided via the npm module

url “$rootDir/../node_modules/detox/Detox-android”

}

}

}

  1. Add the following dependencies and defaultConfig to your app buildscript (i.e. app/build.gradle):

//Please be aware that the minSdkVersion needs to be at least 18.

dependencies {

// …

androidTestImplementation(‘com.wix:detox:+’)

}

// …

android {

// …

defaultConfig {

// …

testBuildType System.getProperty(‘testBuildType’, ‘debug’)

testInstrumentationRunner ‘androidx.test.runner.AndroidJUnitRunner’

}

}

  1. Add Kotlin to your classpath in the root build-script (i.e.android/build.gradle):

buildscript {

ext {

// …

kotlinVersion = ‘1.3.71’

}

// …

dependencies {

// …

classpath “org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlinVersion”

}

}

  1. Create Android Test class:

Add a file android/app/src/androidTest/java/com/[your.package]/DetoxTest.java and fill as in the detox example app for NR. Don’t forget to change the package name to your project’s (create folder androidTest if you need).

  1. Add Detox configuration to package.json

“detox” : {

“configurations”: {

“android.emu.debug”: {

“binaryPath”: “android/app/build/outputs/apk/debug/app-debug.apk”,

“build”:

“cd android && ./gradlew assembleDebug assembleAndroidTest -DtestBuildType=debug && cd ..”,

“type”: “android.emulator”,

“device”: {

“avdName”: <your_emulator_abd_name>

}

},

“android.emu.release”: {

“binaryPath”: “android/app/build/outputs/apk/release/app-release.apk”,

“build”: “cd android && ./gradlew assembleRelease assembleAndroidTest -DtestBuildType=release && cd ..”,

“type”: “android.emulator”,

“device”: {

“avdName”: <your_emulator_abd_name>

}

}

}

}

note: You can get your list of available emulators with the following commands:

cd $ANDROID_SDK_ROOT/emulator

./emulator -list-avds

Step 3: Writing a basic test case.

Let’s assume we want to start a test interacting with a TouchableOpacity. First thing we need is to define a testID so we can reference the ponent via a Detox test:

<View>

<TouchableOpacity testID=’MyUniqueId123′>

<Text>Some button</Text>

</TouchableOpacity>

</View>

Note: since Detox forces us to define IDs for the componentes, it is considered a “gray-box” testing framework due to the fact that the code will reflect the fact that it is tested with Detox through this property.

Create a .spec.js file inside e2e folder (or use the existing file firstTest.spec.js) and paste the following code:

//Define a test block

describe(‘App Tests’, () => {

//Reset the App before each test

beforeEach(async () => {

await device.reloadReactNative();

});

//Define a test case

it(‘test case description’, async () => {

//Your Code here, for example await element(by.id(‘id’)).tap()

});

})

Match the element and perform an action:

await element(by.id(‘MyUniqueId123’)).tap();

Set an expectation on the result:

await expect(element(by.id(‘AnotherUniqueId456’))).toBeVisible();

Step 4: Running the test.

Build the app:

detox build

Then, the tests can be run with the following commands

  1. Android:

detox test -c android.emu.debug

  1. IOS:

detox test -c ios.sim.debug

The command above will run the test (files with extension .spec.js) inside e2e folder.

That’s it. Your first failing Detox test is running!

Make more tests:

You can create more complex tests using the Detox API:


Conclusion

Compartir el post