Repository: codeceptjs/CodeceptJS (js)

Issue:
Android Click Broken When Platform Definition Capitalized
I recently attempted to set up codceptjs for Android automation using the desired capabilities defined on this page (https://codecept.io/mobile/#configuring). The example capabilities are defined like this:

`helpers: {
  Appium: {
    app: "my_app.apk",
    platform: "Android",
    desiredCapabilities: {}
  }
}`

Using these capabilities, every call to I.click() would fail with a 404 error coming back from Appium. After some investigation, I found this line in [WebDriver.js](https://github.com/codeceptjs/CodeceptJS/blob/e956cb8580764f07facf7c07a315775192eee03e/lib/helper/WebDriver.js)

` const clickMethod = this.browser.isMobile && this.browser.capabilities.platformName !== 'android' ? 'touchClick' : 'elementClick';`

I validated that when I pass in a platform of "**Android**", the touch API is called and seems to be incompatible with Android automation. However, if I lower case the platform to "**android**", then the element click method is used and the automation executes properly.

Given this, the best solution would be to make this check case insensitive. If that is not possible, then the documentation (and possibly code generation) needs to be updated to reflect the case sensitive nature of this code. 

Pull request description:
fix(3367): Android Click Broken When Platform Definition Capitalized
## Motivation/Description of the PR
- Resolves #3367 

Applicable helpers:
- [x] WebDriver
- [x] Appium


## Type of change
- [x] :bug: Bug fix

## Checklist:
- [x] Local tests are passed (Run `npm test`)


Patch:
diff --git a/docs/community-helpers.md b/docs/community-helpers.md
index ef758229..4c56ab8c 100644
--- a/docs/community-helpers.md
+++ b/docs/community-helpers.md
@@ -37,6 +37,7 @@ Please **add your own** by editing this page.
 * [codeceptjs-rphelper](https://github.com/reportportal/agent-js-codecept) is a CodeceptJS helper which can publish tests results on ReportPortal after execution.
 * [codeceptjs-xray-helper](https://www.npmjs.com/package/codeceptjs-xray-helper) is a CodeceptJS helper which can publish tests results on [XRAY](https://confluence.xpand-it.com/display/XRAYCLOUD/Import+Execution+Results+-+REST).
 * [codeceptjs-slack-reporter](https://www.npmjs.com/package/codeceptjs-slack-reporter) Get a Slack notification when one or more scenarios fail.
+* [codeceptjs-tesults](https://www.npmjs.com/package/codeceptjs-tesults) Report test results data from CodeceptJS to Tesults with this plugin.
 
 ## Page Object Code Generator
 * [codeceptjs-CodeGenerator](https://github.com/senthillkumar/CodeCeptJS-PageObject) is a CodeceptJS custom wrapper which can create page class with action methods from the page object file(JSON) and project setup(Folder Structure).
diff --git a/docs/reports.md b/docs/reports.md
index 4fb98a19..36a9524b 100644
--- a/docs/reports.md
+++ b/docs/reports.md
@@ -435,3 +435,14 @@ npm i codeceptjs-testrail --save
 
 Now there is new feature, add the configuration to test run of test plan
 ![Attachemnt for failed case](http://g.recordit.co/uQLvQUq7cT.gif)
+
+
+## Tesults
+
+Submit test results data from CodeceptJS to [Tesults](https://www.tesults.com) easily with the [codeceptjs-tesults](https://www.npmjs.com/package/codeceptjs-tesults) plugin. Test results data is submitted automatically after a test run completes.
+
+```sh
+npm i codeceptjs-tesults --save
+```
+
+Once installed, follow the [quick and easy integration instructions](https://www.tesults.com/docs/codeceptjs) to get setup in no time.
diff --git a/lib/helper/WebDriver.js b/lib/helper/WebDriver.js
index f7d91946..8e783d89 100644
--- a/lib/helper/WebDriver.js
+++ b/lib/helper/WebDriver.js
@@ -567,6 +567,9 @@ class WebDriver extends Helper {
       });
     }
 
+    if (this.browser.capabilities && this.browser.capabilities.platformName) {
+      this.browser.capabilities.platformName = this.browser.capabilities.platformName.toLowerCase();
+    }
     return this.browser;
   }
 
diff --git a/lib/utils.js b/lib/utils.js
index 75ea0c0a..31904cc9 100644
--- a/lib/utils.js
+++ b/lib/utils.js
@@ -33,12 +33,7 @@ const isAsyncFunction = module.exports.isAsyncFunction = function (fn) {
 };
 
 module.exports.fileExists = function (filePath) {
-  try {
-    fs.statSync(filePath);
-  } catch (err) {
-    if (err.code === 'ENOENT') return false;
-  }
-  return true;
+  return fs.existsSync(filePath);
 };
 
 module.exports.isFile = function (filePath) {


Test patch:
diff --git a/test/unit/utils_test.js b/test/unit/utils_test.js
index 90c08480..a9e17d33 100644
--- a/test/unit/utils_test.js
+++ b/test/unit/utils_test.js
@@ -7,8 +7,9 @@ const utils = require('../../lib/utils');
 
 describe('utils', () => {
   describe('#fileExists', () => {
-    it('exists', () => expect(utils.fileExists(__filename)));
-    it('not exists', () => expect(!utils.fileExists('not_utils.js')));
+    it('exists', () => expect(utils.fileExists(__filename)).to.be.true);
+    it('not exists', () => expect(utils.fileExists('not_utils.js')).to.be.false);
+    it('not exists if file used as directory', () => expect(utils.fileExists(`${__filename}/not_utils.js`)).to.be.false);
   });
   /* eslint-disable no-unused-vars */
   describe('#getParamNames', () => {