detox 21.0.0-breaking.new-global-lifecycle.0 → 21.0.1-rc.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (304) hide show
  1. package/.eslintrc.js +2 -7
  2. package/Detox-android/com/wix/detox/{21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-javadoc.jar → 21.0.1-rc.0/detox-21.0.1-rc.0-javadoc.jar} +0 -0
  3. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-javadoc.jar.md5 +1 -0
  4. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-javadoc.jar.sha1 +1 -0
  5. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-javadoc.jar.sha256 +1 -0
  6. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-javadoc.jar.sha512 +1 -0
  7. package/Detox-android/com/wix/detox/{21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-sources.jar → 21.0.1-rc.0/detox-21.0.1-rc.0-sources.jar} +0 -0
  8. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-sources.jar.md5 +1 -0
  9. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-sources.jar.sha1 +1 -0
  10. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-sources.jar.sha256 +1 -0
  11. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0-sources.jar.sha512 +1 -0
  12. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.aar +0 -0
  13. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.aar.md5 +1 -0
  14. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.aar.sha1 +1 -0
  15. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.aar.sha256 +1 -0
  16. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.aar.sha512 +1 -0
  17. package/Detox-android/com/wix/detox/{21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.pom → 21.0.1-rc.0/detox-21.0.1-rc.0.pom} +22 -10
  18. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.pom.md5 +1 -0
  19. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.pom.sha1 +1 -0
  20. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.pom.sha256 +1 -0
  21. package/Detox-android/com/wix/detox/21.0.1-rc.0/detox-21.0.1-rc.0.pom.sha512 +1 -0
  22. package/Detox-android/com/wix/detox/maven-metadata.xml +4 -4
  23. package/Detox-android/com/wix/detox/maven-metadata.xml.md5 +1 -1
  24. package/Detox-android/com/wix/detox/maven-metadata.xml.sha1 +1 -1
  25. package/Detox-android/com/wix/detox/maven-metadata.xml.sha256 +1 -1
  26. package/Detox-android/com/wix/detox/maven-metadata.xml.sha512 +1 -1
  27. package/Detox-ios-framework.tbz +0 -0
  28. package/Detox-ios-src.tbz +0 -0
  29. package/Detox-ios-xcuitest.tbz +0 -0
  30. package/README.md +1 -1
  31. package/android/build.gradle +13 -8
  32. package/android/detox/build.gradle +24 -13
  33. package/android/detox/proguard-rules-app.pro +6 -0
  34. package/android/detox/proguard-rules.pro +3 -0
  35. package/android/detox/publish-pom.gradle +5 -1
  36. package/android/detox/publishing.gradle +35 -33
  37. package/android/detox/src/full/java/com/wix/detox/DetoxCrashHandler.kt +1 -1
  38. package/android/detox/src/full/java/com/wix/detox/LaunchArgs.java +9 -0
  39. package/android/detox/src/full/java/com/wix/detox/TestEngineFacade.kt +4 -4
  40. package/android/detox/src/full/java/com/wix/detox/adapters/server/QueryStatusActionHandler.kt +12 -80
  41. package/android/detox/src/full/java/com/wix/detox/adapters/server/WebSocketClient.java +3 -1
  42. package/android/detox/src/full/java/com/wix/detox/common/UIExtensions.kt +28 -0
  43. package/android/detox/src/full/java/com/wix/detox/espresso/DetoxAction.java +37 -3
  44. package/android/detox/src/full/java/com/wix/detox/espresso/DetoxMatcher.java +11 -1
  45. package/android/detox/src/full/java/com/wix/detox/espresso/UiAutomatorHelper.java +1 -1
  46. package/android/detox/src/full/java/com/wix/detox/espresso/action/AdjustSliderToPositionAction.kt +22 -0
  47. package/android/detox/src/{main → full}/java/com/wix/detox/espresso/action/GetAttributesAction.kt +17 -4
  48. package/android/detox/src/full/java/com/wix/detox/espresso/action/RNDetoxAccessibilityAction.kt +46 -0
  49. package/android/detox/src/full/java/com/wix/detox/espresso/common/SliderHelper.kt +75 -0
  50. package/android/detox/src/full/java/com/wix/detox/espresso/common/UiControllerImplReflected.kt +16 -0
  51. package/android/detox/src/full/java/com/wix/detox/espresso/idlingresources/DescriptiveIdlingResource.kt +8 -0
  52. package/android/detox/src/full/java/com/wix/detox/espresso/matcher/ViewMatchers.kt +24 -28
  53. package/android/detox/src/full/java/com/wix/detox/espresso/matcher/WithAccessibilityLabelMatcher.kt +23 -0
  54. package/android/detox/src/full/java/com/wix/detox/espresso/registry/BusyResourcesInquirer.kt +48 -0
  55. package/android/detox/src/full/java/com/wix/detox/inquiry/DetoxBusyResource.kt +92 -0
  56. package/android/detox/src/full/java/com/wix/detox/inquiry/DetoxBusyResourceDescription.kt +26 -0
  57. package/android/detox/src/full/java/com/wix/detox/reactnative/ReactNativeExtension.kt +15 -2
  58. package/android/detox/src/full/java/com/wix/detox/reactnative/ReactNativeIdlingResources.kt +43 -38
  59. package/android/detox/src/full/java/com/wix/detox/reactnative/ReactNativeLoadingMonitor.kt +54 -8
  60. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/AnimatedModuleIdlingResource.java +18 -7
  61. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/AsyncStorageIdlingResource.kt +3 -4
  62. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/BridgeIdlingResource.java +12 -6
  63. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/DetoxBaseIdlingResource.java +2 -0
  64. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/NetworkIdlingResource.java +43 -34
  65. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/timers/DelegatedIdleInterrogationStrategy.kt +7 -27
  66. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/timers/IdleInterrogationStrategy.kt +1 -11
  67. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/timers/TimersIdlingResource.kt +2 -6
  68. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/uimodule/RN66Workaround.kt +13 -4
  69. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/uimodule/UIManagerModuleReflected.kt +1 -1
  70. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/uimodule/UIModuleIdlingResource.kt +4 -6
  71. package/android/detox/src/full/java/com/wix/detox/reactnative/ui/UIExtensions.kt +37 -0
  72. package/android/detox/src/full/java/com/wix/detox/reactnative/utils/RNUtils.kt +6 -0
  73. package/android/detox/src/main/java/com/wix/detox/common/DetoxErrors.java +4 -1
  74. package/android/detox/src/main/java/com/wix/detox/common/TextFileReader.kt +1 -1
  75. package/android/detox/src/main/java/com/wix/detox/espresso/UiControllerSpy.kt +2 -1
  76. package/android/detox/src/main/java/com/wix/detox/espresso/action/common/ReflectUtils.kt +10 -0
  77. package/android/detox/src/main/java/com/wix/detox/espresso/action/common/utils/UiControllerUtils.kt +1 -1
  78. package/android/detox/src/testFull/java/com/wix/detox/UTHelpers.kt +12 -0
  79. package/android/detox/src/testFull/java/com/wix/detox/adapters/server/QueryStatusActionHandlerSpec.kt +35 -94
  80. package/android/detox/src/testFull/java/com/wix/detox/common/UIExtensionsTest.kt +107 -0
  81. package/android/detox/src/testFull/java/com/wix/detox/espresso/action/DetoxMultiTapSpec.kt +4 -3
  82. package/android/detox/src/testFull/java/com/wix/detox/espresso/action/GetAttributesActionTest.kt +22 -9
  83. package/android/detox/src/testFull/java/com/wix/detox/espresso/common/SliderHelperTest.kt +39 -0
  84. package/android/detox/src/testFull/java/com/wix/detox/espresso/matcher/ViewAtIndexMatcherSpec.kt +1 -2
  85. package/android/detox/src/testFull/java/com/wix/detox/espresso/registry/{IRStatusInquirerTest.kt → BusyResourcesInquirerTest.kt} +46 -7
  86. package/android/detox/src/testFull/java/com/wix/detox/{reactnative/idlingresources/IdlingResourceDescriptionSpec.kt → inquiry/DetoxBusyResourceDescriptionSpec.kt} +6 -6
  87. package/android/detox/src/testFull/java/com/wix/detox/inquiry/DetoxBusyResourceSpec.kt +134 -0
  88. package/android/detox/src/testFull/java/com/wix/detox/reactnative/idlingresources/AsyncStorageIdlingResourceSpec.kt +4 -5
  89. package/android/detox/src/testFull/java/com/wix/detox/reactnative/idlingresources/NetworkIdlingResourcesTest.kt +61 -0
  90. package/android/detox/src/testFull/java/com/wix/detox/reactnative/idlingresources/timers/DelegatedIdleInterrogationStrategySpec.kt +3 -11
  91. package/android/detox/src/testFull/java/com/wix/detox/reactnative/idlingresources/timers/TimersIdlingResourceSpec.kt +4 -6
  92. package/android/gradle/wrapper/gradle-wrapper.properties +2 -1
  93. package/android/gradlew +181 -107
  94. package/index.d.ts +239 -83
  95. package/index.js +12 -1
  96. package/internals.d.ts +219 -45
  97. package/internals.js +10 -3
  98. package/local-cli/build-framework-cache.js +1 -1
  99. package/local-cli/build-xcuitest-cache.js +16 -0
  100. package/local-cli/build.js +2 -2
  101. package/local-cli/clean-framework-cache.js +1 -1
  102. package/local-cli/clean-xcuitest-cache.js +19 -0
  103. package/local-cli/cli.js +13 -7
  104. package/local-cli/init.js +61 -21
  105. package/local-cli/rebuild-framework-cache.js +4 -4
  106. package/local-cli/rebuild-xcuitest-cache.js +21 -0
  107. package/local-cli/reset-lock-file.js +16 -0
  108. package/local-cli/run-server.js +12 -1
  109. package/local-cli/start.js +49 -0
  110. package/local-cli/startCommand/AppStartCommand.js +65 -0
  111. package/local-cli/templates/jest.js +13 -10
  112. package/local-cli/test.js +14 -8
  113. package/local-cli/testCommand/TestRunnerCommand.js +126 -77
  114. package/local-cli/testCommand/TestRunnerError.js +13 -0
  115. package/local-cli/testCommand/builder.js +5 -1
  116. package/local-cli/testCommand/middlewares.js +4 -13
  117. package/local-cli/testCommand/warnings.js +0 -3
  118. package/local-cli/utils/cliErrorHandling.js +15 -0
  119. package/local-cli/utils/jestInternals.js +4 -1
  120. package/package.json +46 -26
  121. package/runners/deprecation.js +42 -44
  122. package/runners/jest/globalSetup.js +1 -1
  123. package/runners/jest/globalTeardown.js +1 -1
  124. package/runners/jest/index.d.ts +61 -0
  125. package/runners/jest/index.js +3 -8
  126. package/runners/jest/reporters/DetoxReporter.js +33 -2
  127. package/runners/jest/testEnvironment/index.js +119 -68
  128. package/runners/jest/testEnvironment/listeners/DetoxCoreListener.js +97 -51
  129. package/runners/jest/testEnvironment/listeners/DetoxPlatformFilterListener.js +1 -1
  130. package/runners/jest/testEnvironment/listeners/SpecReporter.js +15 -17
  131. package/runners/jest/testEnvironment/listeners/WorkerAssignReporter.js +3 -7
  132. package/runners/jest/testEnvironment/utils/assertJestCircus27.js +17 -3
  133. package/scripts/build_framework.ios.sh +26 -60
  134. package/scripts/build_local_framework.ios.sh +62 -0
  135. package/scripts/build_local_xcuitest.ios.sh +53 -0
  136. package/scripts/build_xcuitest.ios.sh +23 -0
  137. package/scripts/pack_ios.sh +14 -5
  138. package/scripts/postinstall.js +10 -4
  139. package/src/DetoxWorker.js +112 -64
  140. package/src/android/actions/native.js +16 -0
  141. package/src/android/core/NativeElement.js +72 -20
  142. package/src/android/core/NativeExpect.js +28 -9
  143. package/src/android/core/NativeMatcher.js +31 -10
  144. package/src/android/core/NativeWaitFor.js +8 -0
  145. package/src/android/espressoapi/DetoxAction.js +37 -0
  146. package/src/android/espressoapi/DetoxMatcher.js +24 -0
  147. package/src/android/espressoapi/EspressoDetox.js +1 -1
  148. package/src/android/espressoapi/web/WebElement.js +1 -1
  149. package/src/android/interactions/native.js +25 -18
  150. package/src/android/matchers/index.js +2 -2
  151. package/src/android/matchers/native.js +10 -3
  152. package/src/artifacts/ArtifactsManager.js +14 -47
  153. package/src/artifacts/instruments/ios/SimulatorInstrumentsRecording.js +3 -3
  154. package/src/artifacts/log/android/ADBLogcatRecording.js +11 -28
  155. package/src/artifacts/log/ios/SimulatorLogRecording.js +1 -1
  156. package/src/artifacts/screenshot/SimulatorScreenshotPlugin.js +1 -1
  157. package/src/artifacts/templates/artifact/Artifact.js +1 -1
  158. package/src/artifacts/templates/plugin/ArtifactPlugin.js +2 -2
  159. package/src/artifacts/templates/plugin/TwoSnapshotsPerTestPlugin.js +2 -1
  160. package/src/artifacts/templates/plugin/WholeTestRecorderPlugin.js +3 -2
  161. package/src/artifacts/timeline/TimelineContextTypes.js +7 -0
  162. package/src/artifacts/utils/temporaryPath.js +47 -8
  163. package/src/artifacts/video/SimulatorRecordVideoPlugin.js +1 -1
  164. package/src/client/AsyncWebSocket.js +11 -19
  165. package/src/client/Client.js +35 -3
  166. package/src/client/actions/SyncStatusSchema.json +21 -0
  167. package/src/client/actions/actions.js +38 -0
  168. package/src/client/actions/formatters/SyncStatusFormatter.js +2 -0
  169. package/src/client/actions/formatters/sync-resources/BgThreadFormatter.js +5 -0
  170. package/src/client/actions/formatters/sync-resources/NetworkFormatter.js +1 -1
  171. package/src/configuration/collectCliConfig.js +3 -13
  172. package/src/configuration/composeAppsConfig.js +5 -1
  173. package/src/configuration/composeDeviceConfig.js +1 -1
  174. package/src/configuration/composeLoggerConfig.js +20 -10
  175. package/src/configuration/composeRunnerConfig.js +62 -9
  176. package/src/configuration/index.js +14 -9
  177. package/src/configuration/loadExternalConfig.js +1 -1
  178. package/src/devices/allocation/DeviceAllocator.js +15 -2
  179. package/src/devices/allocation/drivers/AllocationDriverBase.js +10 -2
  180. package/src/devices/allocation/drivers/android/attached/AttachedAndroidAllocDriver.js +10 -1
  181. package/src/devices/allocation/drivers/android/emulator/AVDValidator.js +5 -5
  182. package/src/devices/allocation/drivers/android/emulator/EmulatorAllocDriver.js +28 -29
  183. package/src/devices/allocation/drivers/android/emulator/EmulatorAllocationHelper.js +1 -1
  184. package/src/devices/allocation/drivers/android/emulator/EmulatorLauncher.js +6 -5
  185. package/src/devices/allocation/drivers/android/emulator/EmulatorVersionResolver.js +4 -6
  186. package/src/devices/allocation/drivers/android/emulator/launchEmulatorProcess.js +4 -17
  187. package/src/devices/allocation/drivers/android/genycloud/GenyAllocDriver.js +27 -18
  188. package/src/devices/allocation/drivers/android/genycloud/GenyInstanceAllocationHelper.js +1 -1
  189. package/src/devices/allocation/drivers/ios/SimulatorAllocDriver.js +12 -7
  190. package/src/devices/allocation/factories/base.js +1 -1
  191. package/src/devices/common/drivers/android/exec/ADB.js +9 -0
  192. package/src/devices/common/drivers/android/genycloud/exec/GenyCloudExec.js +1 -1
  193. package/src/devices/common/drivers/android/genycloud/services/GenyInstanceNaming.js +3 -3
  194. package/src/devices/common/drivers/android/genycloud/services/GenyRecipesService.js +1 -1
  195. package/src/devices/common/drivers/android/tools/AppInstallHelper.js +4 -4
  196. package/src/devices/common/drivers/android/tools/EmulatorTelnet.js +1 -1
  197. package/src/devices/common/drivers/android/tools/{FileXfer.js → FileTransfer.js} +2 -2
  198. package/src/devices/common/drivers/android/tools/FreeDeviceFinder.js +1 -1
  199. package/src/devices/common/drivers/android/tools/MonitoredInstrumentation.js +1 -1
  200. package/src/devices/common/drivers/android/tools/TempFileTransfer.js +14 -0
  201. package/src/devices/common/drivers/ios/tools/AppleSimUtils.js +21 -4
  202. package/src/devices/lifecycle/GenyGlobalLifecycleHandler.js +13 -15
  203. package/src/devices/runtime/RuntimeDevice.js +24 -12
  204. package/src/devices/runtime/drivers/DeviceDriverBase.js +2 -1
  205. package/src/devices/runtime/drivers/android/AndroidDriver.js +17 -8
  206. package/src/devices/runtime/drivers/ios/SimulatorDriver.js +42 -2
  207. package/src/devices/runtime/drivers/ios/XCUITestUtils.js +209 -0
  208. package/src/devices/runtime/drivers/ios/allowNetworkPermissionsXCUITest.scpt +14 -0
  209. package/src/devices/runtime/factories/android.js +6 -5
  210. package/src/devices/runtime/factories/base.js +3 -2
  211. package/src/errors/DetoxConfigErrorComposer.js +18 -3
  212. package/src/errors/DetoxError.js +5 -1
  213. package/src/ios/expectTwo.js +199 -78
  214. package/src/ipc/IPCClient.js +36 -27
  215. package/src/ipc/IPCServer.js +40 -21
  216. package/src/ipc/SessionState.js +60 -0
  217. package/src/logger/DetoxLogger.js +287 -154
  218. package/src/logger/index.js +5 -0
  219. package/src/logger/utils/BunyanLogger.js +105 -0
  220. package/src/logger/utils/CategoryThreadDispatcher.js +37 -0
  221. package/src/logger/utils/DetoxLogFinalizer.js +166 -0
  222. package/src/logger/utils/MessageStack.js +35 -0
  223. package/src/logger/utils/ThreadDispatcher.js +61 -0
  224. package/src/logger/{customConsoleLogger.js → utils/customConsoleLogger.js} +23 -6
  225. package/src/logger/utils/getMainCategory.js +5 -0
  226. package/src/logger/utils/sanitizeBunyanContext.js +30 -0
  227. package/src/logger/utils/streams/BunyanTransformer.js +72 -0
  228. package/src/logger/utils/streams/ChromeTraceTransformer.js +132 -0
  229. package/src/logger/utils/streams/DetoxJSONLParser.js +31 -0
  230. package/src/logger/utils/streams/JSONLStringer.js +55 -0
  231. package/src/logger/utils/streams/index.js +7 -0
  232. package/src/logger/utils/streams/transformers.js +39 -0
  233. package/src/logger/utils/tracerLegacy.js +37 -0
  234. package/src/realms/DetoxContext.js +83 -66
  235. package/src/realms/DetoxInternalsFacade.js +9 -13
  236. package/src/realms/DetoxPrimaryContext.js +117 -74
  237. package/src/realms/DetoxSecondaryContext.js +32 -35
  238. package/src/{symbols.js → realms/symbols.js} +16 -22
  239. package/src/server/DetoxConnection.js +18 -23
  240. package/src/server/DetoxServer.js +7 -10
  241. package/src/server/DetoxSession.js +9 -6
  242. package/src/server/DetoxSessionManager.js +2 -1
  243. package/src/server/handlers/AnonymousConnectionHandler.js +1 -0
  244. package/src/server/handlers/RegisteredConnectionHandler.js +1 -2
  245. package/src/servicelocator/android/index.js +2 -2
  246. package/src/utils/ExclusiveLockfile.js +1 -0
  247. package/src/utils/Timer.js +59 -36
  248. package/src/utils/argparse.js +11 -27
  249. package/src/utils/childProcess/exec.js +4 -2
  250. package/src/utils/childProcess/spawn.js +1 -1
  251. package/src/utils/dateUtils.js +5 -0
  252. package/src/utils/environment.js +55 -16
  253. package/src/utils/errorUtils.js +24 -3
  254. package/src/utils/invocationTraceDescriptions.js +44 -0
  255. package/src/utils/isPromise.js +8 -1
  256. package/src/utils/logger.js +2 -2
  257. package/src/utils/pathUtils.js +11 -0
  258. package/src/utils/shellUtils.js +17 -0
  259. package/src/utils/traceInvocationCall.js +21 -0
  260. package/src/utils/traceMethods.js +15 -0
  261. package/src/validation/ios/IosSimulatorEnvValidator.js +7 -4
  262. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-javadoc.jar.md5 +0 -1
  263. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-javadoc.jar.sha1 +0 -1
  264. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-javadoc.jar.sha256 +0 -1
  265. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-javadoc.jar.sha512 +0 -1
  266. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-sources.jar.md5 +0 -1
  267. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-sources.jar.sha1 +0 -1
  268. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-sources.jar.sha256 +0 -1
  269. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0-sources.jar.sha512 +0 -1
  270. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.aar +0 -0
  271. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.aar.md5 +0 -1
  272. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.aar.sha1 +0 -1
  273. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.aar.sha256 +0 -1
  274. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.aar.sha512 +0 -1
  275. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.pom.md5 +0 -1
  276. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.pom.sha1 +0 -1
  277. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.pom.sha256 +0 -1
  278. package/Detox-android/com/wix/detox/21.0.0-breaking.new-global-lifecycle.0/detox-21.0.0-breaking.new-global-lifecycle.0.pom.sha512 +0 -1
  279. package/Detox-ios.tbz +0 -0
  280. package/android/detox/src/full/java/com/wix/detox/espresso/registry/IRStatusInquirer.kt +0 -24
  281. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/DescriptiveIdlingResource.kt +0 -10
  282. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/IdlingResourceDescription.kt +0 -20
  283. package/android/detox/src/full/java/com/wix/detox/reactnative/idlingresources/timers/DefaultIdleInterrogationStrategy.kt +0 -84
  284. package/android/detox/src/main/java/com/wix/detox/espresso/action/AdjustSliderToPositionAction.kt +0 -36
  285. package/android/detox/src/testFull/java/com/wix/detox/espresso/action/AdjustSliderToPositionActionTest.kt +0 -59
  286. package/android/detox/src/testFull/java/com/wix/detox/reactnative/idlingresources/timers/DefaultIdleInterrogationStrategySpec.kt +0 -115
  287. package/local-cli/build.test.js +0 -104
  288. package/local-cli/run-server.test.js +0 -23
  289. package/local-cli/test.test.js +0 -515
  290. package/runners/jest/deprecation.js +0 -25
  291. package/runners/jest/testEnvironment/utils/assertJestCircus27.test.js +0 -23
  292. package/scripts/build_universal_framework.sh +0 -14
  293. package/scripts/build_universal_framework_legacy.sh +0 -76
  294. package/scripts/build_universal_framework_modern.sh +0 -28
  295. package/src/configuration/utils/warnings.js +0 -12
  296. package/src/devices/common/drivers/android/tools/TempFileXfer.js +0 -16
  297. package/src/ipc/state.js +0 -76
  298. package/src/logger/DetoxTraceEventBuilder.js +0 -21
  299. package/src/logger/DetoxTracer.js +0 -133
  300. package/src/logger/TraceThreadDispatcher.js +0 -52
  301. package/src/realms/index.js +0 -10
  302. package/src/utils/ChromeTracingExporter.js +0 -53
  303. package/src/utils/streamUtils.js +0 -214
  304. package/src/utils/trace.js +0 -19
@@ -1,43 +1,23 @@
1
+
1
2
  package com.wix.detox.reactnative.idlingresources.timers
2
3
 
3
- import com.facebook.react.bridge.NativeModule
4
4
  import com.facebook.react.bridge.ReactContext
5
- import com.wix.detox.common.RNDropSupportTodo
6
- import com.wix.detox.reactnative.helpers.RNHelpers
7
- import org.joor.Reflect
5
+ import com.facebook.react.modules.core.TimingModule
8
6
 
9
7
  private const val BUSY_WINDOW_THRESHOLD = 1500L
10
8
 
11
- private class RN62TimingModuleReflected(private val timingModule: NativeModule) {
12
- fun hasActiveTimers(): Boolean = Reflect.on(timingModule).call("hasActiveTimersInRange", BUSY_WINDOW_THRESHOLD).get()
13
- }
14
-
15
9
  /**
16
10
  * Delegates the interrogation to the native module itself, added
17
11
  * [here](https://github.com/facebook/react-native/pull/27539) in the context
18
12
  * of RN v0.62 (followed by a previous refactor and rename of the class).
19
13
  */
20
- @RNDropSupportTodo(62, """
21
- When min RN version supported by Detox is 0.62.x (or higher), can (and
22
- should) remove any usage of reflection here.
23
- That includes the unit test's stub being used for that reason in particular.
24
- """)
25
- class DelegatedIdleInterrogationStrategy(timingModule: NativeModule): IdleInterrogationStrategy {
26
- private val timingModuleReflected = RN62TimingModuleReflected(timingModule)
27
-
28
- override fun isIdleNow(): Boolean = !timingModuleReflected.hasActiveTimers()
14
+ class DelegatedIdleInterrogationStrategy(private val timingModule: TimingModule): IdleInterrogationStrategy {
15
+ override fun isIdleNow(): Boolean = !timingModule.hasActiveTimersInRange(BUSY_WINDOW_THRESHOLD)
29
16
 
30
17
  companion object {
31
- fun createIfSupported(reactContext: ReactContext): DelegatedIdleInterrogationStrategy? {
32
- val module = RNHelpers.getNativeModule(reactContext, "com.facebook.react.modules.core.TimingModule")
33
- ?: return null
34
-
35
- return try {
36
- module.javaClass.getDeclaredMethod("hasActiveTimersInRange", Long::class.java)
37
- DelegatedIdleInterrogationStrategy(module)
38
- } catch (ex: Exception) {
39
- null
40
- }
18
+ fun create(reactContext: ReactContext): DelegatedIdleInterrogationStrategy {
19
+ val timingModule = reactContext.getNativeModule(TimingModule::class.java)!!
20
+ return DelegatedIdleInterrogationStrategy(timingModule)
41
21
  }
42
22
  }
43
23
  }
@@ -1,6 +1,5 @@
1
1
  package com.wix.detox.reactnative.idlingresources.timers
2
2
 
3
- import android.util.Log
4
3
  import com.facebook.react.bridge.ReactContext
5
4
  import com.wix.detox.common.UIThread
6
5
  import java.util.concurrent.Callable
@@ -13,14 +12,5 @@ fun getInterrogationStrategy(reactContext: ReactContext): IdleInterrogationStrat
13
12
  // Getting a native-module (inside) also initializes it if needed. That has to run on a
14
13
  // looper thread, and the easiest to make sure that happens is to use the main thread.
15
14
  UIThread.runSync(Callable {
16
- DelegatedIdleInterrogationStrategy.createIfSupported(reactContext)?.let {
17
- return@Callable it
18
- }
19
-
20
- DefaultIdleInterrogationStrategy.createIfSupported(reactContext)?.let {
21
- return@Callable it
22
- }
23
-
24
- Log.e(TimersIdlingResource.LOG_TAG, "Failed to determine proper implementation-strategy for timers idling resource")
25
- null
15
+ return@Callable DelegatedIdleInterrogationStrategy.create(reactContext)
26
16
  })
@@ -2,9 +2,7 @@ package com.wix.detox.reactnative.idlingresources.timers
2
2
 
3
3
  import android.view.Choreographer
4
4
  import androidx.test.espresso.IdlingResource
5
-
6
5
  import com.wix.detox.reactnative.idlingresources.DetoxBaseIdlingResource
7
- import com.wix.detox.reactnative.idlingresources.IdlingResourceDescription
8
6
 
9
7
  class TimersIdlingResource @JvmOverloads constructor(
10
8
  private val interrogationStrategy: IdleInterrogationStrategy,
@@ -14,10 +12,8 @@ class TimersIdlingResource @JvmOverloads constructor(
14
12
  private var callback: IdlingResource.ResourceCallback? = null
15
13
 
16
14
  override fun getName(): String = this.javaClass.name
17
-
18
- override fun getDescription(): IdlingResourceDescription {
19
- return IdlingResourceDescription.Builder().name("timers").build();
20
- }
15
+ override fun getDebugName(): String = "timers"
16
+ override fun getBusyHint(): Map<String, Any>? = null
21
17
 
22
18
  override fun registerIdleTransitionCallback(callback: IdlingResource.ResourceCallback?) {
23
19
  this.callback = callback
@@ -2,6 +2,7 @@ package com.wix.detox.reactnative.idlingresources.uimodule
2
2
 
3
3
  import android.util.Log
4
4
  import android.view.View
5
+ import com.facebook.react.uimanager.IllegalViewOperationException
5
6
  import com.wix.detox.common.DetoxLog.Companion.LOG_TAG
6
7
  import com.wix.detox.reactnative.ReactNativeInfo
7
8
  import java.lang.ref.WeakReference
@@ -19,9 +20,7 @@ class RN66Workaround {
19
20
  fun isScarceUISwitchCommandStuckInQueue(uiManagerModuleReflected: UIManagerModuleReflected): Boolean {
20
21
  var isStuckSwitchOperation = false
21
22
 
22
- val rnVersion = ReactNativeInfo.rnVersion()
23
-
24
- if (rnVersion.minor >= 66 && uiManagerModuleReflected.getUIOpsCount() >= 1) {
23
+ if (isRelevantRNVersion() && uiManagerModuleReflected.getUIOpsCount() >= 1) {
25
24
  val nextUIOperation = uiManagerModuleReflected.getNextUIOpReflected()
26
25
  val view = getUIOpView(uiManagerModuleReflected, nextUIOperation)
27
26
  val isReactSwitch = isReactSwitch(view)
@@ -46,10 +45,20 @@ class RN66Workaround {
46
45
  return isStuckSwitchOperation
47
46
  }
48
47
 
48
+ private fun isRelevantRNVersion(): Boolean {
49
+ val rnVersion = ReactNativeInfo.rnVersion()
50
+ return rnVersion.minor == 66 || (rnVersion.minor == 67 && rnVersion.patch < 4)
51
+ }
52
+
49
53
  private fun getUIOpView(uiManagerModuleReflected: UIManagerModuleReflected, uiOperation: DispatchCommandOperationReflected?): View? {
50
54
  val nativeViewHierarchyManager = uiManagerModuleReflected.nativeViewHierarchyManager() ?: return null
51
55
  val tag = uiOperation?.tag ?: return null
52
- return nativeViewHierarchyManager.getViewClass(tag)
56
+ return try {
57
+ nativeViewHierarchyManager.getViewClass(tag)
58
+ } catch(e: IllegalViewOperationException) {
59
+ Log.e(LOG_TAG, "failed to get view from tag ", e.cause)
60
+ null
61
+ }
53
62
  }
54
63
 
55
64
  private fun isReactSwitch(view: View?) = try {
@@ -9,12 +9,12 @@ import org.joor.Reflect
9
9
  private const val CLASS_UI_MANAGER_MODULE = "com.facebook.react.uimanager.UIManagerModule"
10
10
  private const val METHOD_GET_NATIVE_MODULE = "getNativeModule"
11
11
  private const val METHOD_GET_UI_IMPLEMENTATION = "getUIImplementation"
12
+ private const val METHOD_IS_EMPTY = "isEmpty"
12
13
  private const val FIELD_UI_OPERATION_QUEUE = "mOperationsQueue"
13
14
  private const val FIELD_DISPATCH_RUNNABLES = "mDispatchUIRunnables"
14
15
  private const val FIELD_DISPATCH_RUNNABLES_LOCK = "mDispatchRunnablesLock"
15
16
  private const val FIELD_NON_BATCHED_OPS = "mNonBatchedOperations"
16
17
  private const val FIELD_NON_BATCHED_OPS_LOCK = "mNonBatchedOperationsLock"
17
- private const val METHOD_IS_EMPTY = "isEmpty"
18
18
 
19
19
  class UIManagerModuleReflected(private val reactContext: ReactContext) {
20
20
 
@@ -6,7 +6,6 @@ import androidx.test.espresso.IdlingResource.ResourceCallback
6
6
  import com.facebook.react.bridge.ReactContext
7
7
  import com.wix.detox.reactnative.helpers.RNHelpers
8
8
  import com.wix.detox.reactnative.idlingresources.DetoxBaseIdlingResource
9
- import com.wix.detox.reactnative.idlingresources.IdlingResourceDescription
10
9
  import org.joor.ReflectException
11
10
 
12
11
  /**
@@ -21,11 +20,10 @@ class UIModuleIdlingResource(private val reactContext: ReactContext)
21
20
  private var callback: ResourceCallback? = null
22
21
 
23
22
  override fun getName(): String = UIModuleIdlingResource::class.java.name
24
- override fun getDescription() =
25
- IdlingResourceDescription.Builder()
26
- .name("ui")
27
- .addDescription("reason", "UI rendering activity")
28
- .build()
23
+ override fun getDebugName(): String = " ui"
24
+ override fun getBusyHint(): Map<String, Any> {
25
+ return mapOf("reason" to "UI rendering activity")
26
+ }
29
27
 
30
28
  override fun checkIdle(): Boolean {
31
29
  try {
@@ -0,0 +1,37 @@
1
+ package com.wix.detox.reactnative.ui
2
+
3
+ import android.view.View
4
+ import android.widget.TextView
5
+ import com.wix.detox.common.traverseViewHierarchy
6
+ import com.wix.detox.reactnative.utils.isReactNativeObject
7
+
8
+ fun View.getAccessibilityLabel(
9
+ isReactNativeObjectFn: (Any) -> Boolean = { isReactNativeObject(it) }
10
+ ): CharSequence? =
11
+ if (isReactNativeObjectFn(this)) {
12
+ val subLabels = collectAccessibilityLabelsFromHierarchy(this)
13
+ if (subLabels.isEmpty()) null else subLabels.joinToString(" ")
14
+ } else {
15
+ getRawAccessibilityLabel(this)
16
+ }
17
+
18
+ private fun collectAccessibilityLabelsFromHierarchy(
19
+ rootView: View,
20
+ subLabels: MutableList<CharSequence> = mutableListOf(),
21
+ ): List<CharSequence> {
22
+ traverseViewHierarchy(rootView) { view ->
23
+ getRawAccessibilityLabel(view)?.let { rawLabel ->
24
+ subLabels.add(rawLabel)
25
+ false
26
+ } ?: true
27
+
28
+ }
29
+ return subLabels
30
+ }
31
+
32
+ private fun getRawAccessibilityLabel(view: View): CharSequence? =
33
+ if (view.contentDescription != null) {
34
+ view.contentDescription
35
+ } else if (view is TextView) {
36
+ view.text
37
+ } else null
@@ -0,0 +1,6 @@
1
+ package com.wix.detox.reactnative.utils
2
+
3
+ private const val REACT_NATIVE_PACKAGE = "com.facebook.react"
4
+
5
+ fun isReactNativeObject(obj: Any): Boolean =
6
+ obj.javaClass.canonicalName?.startsWith(REACT_NATIVE_PACKAGE) == true
@@ -5,7 +5,6 @@ public interface DetoxErrors {
5
5
  public DetoxRuntimeException(Throwable cause) {
6
6
  super(cause);
7
7
  }
8
-
9
8
  public DetoxRuntimeException(String message) {
10
9
  super(message);
11
10
  }
@@ -31,5 +30,9 @@ public interface DetoxErrors {
31
30
  public DetoxIllegalArgumentException(String message) {
32
31
  super(message);
33
32
  }
33
+
34
+ public DetoxIllegalArgumentException(Throwable cause) {
35
+ super(cause);
36
+ }
34
37
  }
35
38
  }
@@ -3,5 +3,5 @@ package com.wix.detox.common
3
3
  import java.io.File
4
4
 
5
5
  internal class TextFileReader(private val fileName: String) {
6
- fun read() = File(fileName).inputStream().readBytes().toString(Charsets.UTF_8)
6
+ fun read() = File(fileName).readText(Charsets.UTF_8)
7
7
  }
@@ -1,10 +1,11 @@
1
+
1
2
  package com.wix.detox.espresso
2
3
 
3
4
  import androidx.test.espresso.UiController
4
5
  import com.wix.detox.common.proxy.CallInfo
5
6
  import com.wix.detox.common.proxy.SpyingInvocationHandler
6
7
  import com.wix.detox.common.proxy.MethodsSpy
7
- import com.wix.detox.espresso.common.utils.getUiController
8
+ import com.wix.detox.espresso.action.common.utils.getUiController
8
9
  import org.joor.Reflect
9
10
 
10
11
  class UiControllerSpy: MethodsSpy("uiController") {
@@ -0,0 +1,10 @@
1
+ package com.wix.detox.espresso.action.common
2
+
3
+ object ReflectUtils {
4
+ fun isAssignableFrom(source: Any, className: String) =
5
+ try {
6
+ Class.forName(className).isAssignableFrom(source.javaClass)
7
+ } catch (ex: ClassNotFoundException) {
8
+ false
9
+ }
10
+ }
@@ -1,6 +1,6 @@
1
1
  @file:JvmName("UiControllerUtils")
2
2
 
3
- package com.wix.detox.espresso.common.utils
3
+ package com.wix.detox.espresso.action.common.utils
4
4
 
5
5
  import androidx.test.espresso.Espresso
6
6
  import androidx.test.espresso.UiController
@@ -1,8 +1,20 @@
1
1
  package com.wix.detox
2
2
 
3
+ import android.view.View
4
+ import android.view.ViewGroup
5
+ import org.mockito.ArgumentMatchers.eq
6
+ import org.mockito.kotlin.whenever
3
7
  import java.util.concurrent.ExecutorService
4
8
  import java.util.concurrent.TimeUnit
5
9
 
6
10
  object UTHelpers {
7
11
  fun yieldToOtherThreads(executor: ExecutorService) = executor.awaitTermination(100L, TimeUnit.MILLISECONDS)
12
+
13
+ fun mockViewHierarchy(parent: ViewGroup, vararg children: View) {
14
+ whenever(parent.childCount).thenReturn(children.size)
15
+
16
+ children.forEachIndexed { index, view ->
17
+ whenever(parent.getChildAt(eq(index))).thenReturn(view)
18
+ }
19
+ }
8
20
  }
@@ -1,9 +1,8 @@
1
1
  package com.wix.detox.adapters.server
2
2
 
3
- import androidx.test.espresso.IdlingResource
4
3
  import com.wix.detox.TestEngineFacade
5
- import com.wix.detox.reactnative.idlingresources.DescriptiveIdlingResource
6
- import com.wix.detox.reactnative.idlingresources.IdlingResourceDescription
4
+ import com.wix.detox.inquiry.DetoxBusyResource
5
+ import com.wix.detox.inquiry.DetoxBusyResourceDescription
7
6
  import org.mockito.kotlin.eq
8
7
  import org.mockito.kotlin.mock
9
8
  import org.mockito.kotlin.verify
@@ -31,103 +30,45 @@ object QueryStatusActionHandlerSpec : Spek({
31
30
  }
32
31
  }
33
32
 
34
- fun queryStatusHandler() = QueryStatusActionHandler(outboundServerAdapter, testEngineFacade)
33
+ fun uut() = QueryStatusActionHandler(outboundServerAdapter, testEngineFacade)
35
34
 
36
- it("should return idle app status") {
37
- queryStatusHandler().handle(params, messageId)
38
- val expectedData = mapOf("status" to mapOf("app_status" to "idle"))
39
- verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
40
- }
41
-
42
- fun createMockedDescriptiveResource(description: IdlingResourceDescription):
43
- DescriptiveIdlingResource {
44
- val resource: DescriptiveIdlingResource = mock()
45
- whenever(resource.getDescription()).thenReturn(description)
46
- return resource
47
- }
48
-
49
- it("should return busy app status with descriptive resource") {
50
- val fakeDescription = IdlingResourceDescription.Builder()
51
- .name("foo")
52
- .addDescription("bar", "baz")
53
- .addDescription("qux", "quux")
54
- .build()
55
-
56
- val busyResources: List<IdlingResource> = listOf(
57
- createMockedDescriptiveResource(fakeDescription)
58
- )
59
- whenever(testEngineFacade.getBusyIdlingResources()).thenReturn(busyResources)
35
+ describe("given an idle app") {
36
+ it("should send an idle status indication") {
37
+ val expectedData = mapOf("status" to mapOf("app_status" to "idle"))
60
38
 
61
- queryStatusHandler().handle(params, messageId)
62
-
63
- val expectedBusyResourceDescription = listOf(
64
- mapOf("name" to "foo", "description" to mapOf("bar" to "baz", "qux" to "quux"))
65
- )
66
- val expectedData = mapOf("status" to mapOf("app_status" to "busy", "busy_resources" to expectedBusyResourceDescription))
67
- verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
68
- }
69
-
70
- abstract class LooperIdlingResource: IdlingResource {}
71
-
72
- fun createMockedLooperIdlingResource(resourceName: String): LooperIdlingResource {
73
- val resource: LooperIdlingResource = mock()
74
- whenever(resource.name).thenReturn(resourceName)
75
- return resource
39
+ uut().handle(params, messageId)
40
+ verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
41
+ }
76
42
  }
77
43
 
78
- it("should return busy app status with looper resources") {
79
- val busyResources: List<IdlingResource> = listOf(
80
- createMockedLooperIdlingResource("mqt_js"),
81
- createMockedLooperIdlingResource("mqt_native"),
82
- createMockedLooperIdlingResource("unmapped")
83
- )
84
- whenever(testEngineFacade.getBusyIdlingResources()).thenReturn(busyResources)
85
-
86
- queryStatusHandler().handle(params, messageId)
44
+ describe("given a busy app") {
45
+ fun aBusyResourceDescription(description: Map<String, Any>): DetoxBusyResourceDescription =
46
+ mock {
47
+ on { json() }.thenReturn(description)
48
+ }
49
+
50
+ fun aBusyResource(identifier: String): DetoxBusyResource {
51
+ val mockedDescription = aBusyResourceDescription(mapOf("mock" to identifier))
52
+ return mock {
53
+ on { getDescription() }.thenReturn(mockedDescription)
54
+ }
55
+ }
87
56
 
88
- val expectedBusyResourceDescription = listOf(
89
- mapOf(
90
- "name" to "looper",
91
- "description" to mapOf(
92
- "thread" to "\"mqt_js\" (JS Thread)",
93
- "execution_type" to "JavaScript code"
94
- )
95
- ),
96
- mapOf(
97
- "name" to "looper",
98
- "description" to mapOf(
99
- "thread" to "\"mqt_native\" (Native Modules Thread)",
100
- "execution_type" to "native module calls"
57
+ it("should send a descriptive busy-status indication") {
58
+ val busyResource = aBusyResource("some-resource")
59
+ val busyResource2 = aBusyResource("yet-another-resource")
60
+ val expectedData = mapOf<String, Any>("status" to mapOf(
61
+ "app_status" to "busy",
62
+ "busy_resources" to listOf(
63
+ mapOf("mock" to "some-resource"),
64
+ mapOf("mock" to "yet-another-resource"),
101
65
  )
102
- ),
103
- mapOf(
104
- "name" to "looper",
105
- "description" to mapOf("thread" to "\"unmapped\"")
106
- )
107
- )
108
- val expectedData = mapOf("status" to mapOf("app_status" to "busy", "busy_resources" to expectedBusyResourceDescription))
109
- verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
110
- }
66
+ ))
67
+ whenever(testEngineFacade.getAllBusyResources()).thenReturn(listOf(busyResource, busyResource2))
111
68
 
112
- fun createMockedIdlingResource(name: String): IdlingResource {
113
- val resource: IdlingResource = mock()
114
- whenever(resource.name).thenReturn(name)
115
- return resource
116
- }
117
-
118
- it("should return busy app status with unknown resource") {
119
- val busyResources: List<IdlingResource> = listOf(
120
- createMockedIdlingResource( "quux")
121
- )
122
- whenever(testEngineFacade.getBusyIdlingResources()).thenReturn(busyResources)
123
-
124
- queryStatusHandler().handle(params, messageId)
125
-
126
- val expectedBusyResourceDescription = listOf(
127
- mapOf("name" to "unknown", "description" to mapOf("identifier" to "quux"))
128
- )
129
- val expectedData = mapOf("status" to mapOf("app_status" to "busy", "busy_resources" to expectedBusyResourceDescription))
130
- verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
69
+ uut().handle(params, messageId)
70
+ verify(outboundServerAdapter).sendMessage(eq("currentStatusResult"), eq(expectedData), eq(messageId))
71
+ }
131
72
  }
132
- }
73
+ }
133
74
  })
@@ -0,0 +1,107 @@
1
+ package com.wix.detox.common
2
+
3
+ import android.view.View
4
+ import android.view.ViewGroup
5
+ import android.widget.TextView
6
+ import com.wix.detox.UTHelpers.mockViewHierarchy
7
+ import com.wix.detox.reactnative.ui.getAccessibilityLabel
8
+ import org.assertj.core.api.Assertions
9
+ import org.junit.Test
10
+ import org.junit.runner.RunWith
11
+ import org.mockito.kotlin.doReturn
12
+ import org.mockito.kotlin.mock
13
+ import org.mockito.kotlin.whenever
14
+ import org.robolectric.RobolectricTestRunner
15
+
16
+ @RunWith(RobolectricTestRunner::class)
17
+ class UIExtensionsTest {
18
+ private val alwaysReactNativeObjFn: (Any) -> Boolean = { true }
19
+ private val neverReactNativeObjFn: (Any) -> Boolean = { false }
20
+
21
+ private fun withContentDescription(value: String, v: View) { whenever(v.contentDescription).doReturn(value) }
22
+ private fun withText(value: String, v: TextView) { whenever(v.text).doReturn(value) }
23
+
24
+ @Test
25
+ fun `should return accessibility label according to content-description`() {
26
+ val view: View = mock()
27
+
28
+ val contentDescription = "content-description-mock"
29
+ withContentDescription(contentDescription, view)
30
+
31
+ val label = view.getAccessibilityLabel()
32
+ Assertions.assertThat(label).isEqualTo(contentDescription)
33
+ }
34
+
35
+ @Test
36
+ fun `should return accessibility label according to children's content-description, recursively`() {
37
+ val contentDescription1st = "cd.1"
38
+ val contentDescription2nd = "cd.2"
39
+ val expectedLabel = "$contentDescription1st $contentDescription2nd"
40
+
41
+
42
+ val parent: ViewGroup = mock()
43
+ val sibling1: ViewGroup = mock()
44
+ val sibling2: ViewGroup = mock<ViewGroup>().also {
45
+ withContentDescription(contentDescription2nd, it)
46
+ }
47
+ val grandchild: View = mock<View>().also {
48
+ withContentDescription(contentDescription1st, it)
49
+ }
50
+
51
+ mockViewHierarchy(parent, sibling1, sibling2)
52
+ mockViewHierarchy(sibling1, grandchild)
53
+
54
+ val label = parent.getAccessibilityLabel(alwaysReactNativeObjFn)
55
+ Assertions.assertThat(label).isEqualTo(expectedLabel)
56
+ }
57
+
58
+ @Test
59
+ fun `should return accessibility label according to children's text, on top of label`() {
60
+ val text = "some mocked text"
61
+
62
+ val parent: ViewGroup = mock()
63
+ val grandchild: TextView = mock<TextView>().also {
64
+ withText(text, it)
65
+ }
66
+ mockViewHierarchy(parent, grandchild)
67
+
68
+ val label = parent.getAccessibilityLabel(alwaysReactNativeObjFn)
69
+ Assertions.assertThat(label).isEqualTo(text)
70
+ }
71
+
72
+ @Test
73
+ fun `should not return accessibility label if content description not set in view nor its descendants`() {
74
+ val parent: ViewGroup = mock()
75
+ val child: View = mock()
76
+
77
+ mockViewHierarchy(parent, child)
78
+
79
+ val label = parent.getAccessibilityLabel(alwaysReactNativeObjFn)
80
+ Assertions.assertThat(label).isNull()
81
+ }
82
+
83
+ @Test
84
+ fun `should not return accessibility label based on children for non-RN views`() {
85
+ val childContentDescription = "content-description-mock"
86
+
87
+ val parent: ViewGroup = mock()
88
+ val child: View = mock<View>().also {
89
+ withContentDescription(childContentDescription, it)
90
+ }
91
+ mockViewHierarchy(parent, child)
92
+
93
+ val label = parent.getAccessibilityLabel(neverReactNativeObjFn)
94
+ Assertions.assertThat(label).isNull()
95
+ }
96
+
97
+ @Test
98
+ fun `should return accessibility label for non-RN views`() {
99
+ val view: View = mock()
100
+
101
+ val contentDescription = "content-description-mock"
102
+ withContentDescription(contentDescription, view)
103
+
104
+ val label = view.getAccessibilityLabel(neverReactNativeObjFn)
105
+ Assertions.assertThat(label).isEqualTo(contentDescription)
106
+ }
107
+ }
@@ -11,6 +11,7 @@ import org.assertj.core.api.Assertions.assertThat
11
11
  import org.mockito.kotlin.*
12
12
  import org.spekframework.spek2.Spek
13
13
  import org.spekframework.spek2.style.specification.describe
14
+ import java.lang.NullPointerException
14
15
  import kotlin.test.assertFailsWith
15
16
 
16
17
  object DetoxMultiTapSpec: Spek({
@@ -136,17 +137,17 @@ object DetoxMultiTapSpec: Spek({
136
137
  }
137
138
 
138
139
  it("should throw if no UI-controller provided") {
139
- assertFailsWith(KotlinNullPointerException::class) {
140
+ assertFailsWith(NullPointerException::class) {
140
141
  uut(1).sendTap(null, coordinates, precision, -1, -1)
141
142
  }
142
143
  }
143
144
 
144
145
  it("should throw if no coordinates / precision are provided") {
145
- assertFailsWith(KotlinNullPointerException::class) {
146
+ assertFailsWith(NullPointerException::class) {
146
147
  uut(1).sendTap(uiController, null, precision, -1, -1)
147
148
  }
148
149
 
149
- assertFailsWith(KotlinNullPointerException::class) {
150
+ assertFailsWith(NullPointerException::class) {
150
151
  uut(1).sendTap(uiController, coordinates, null, -1, -1)
151
152
  }
152
153
  }