WebdriverIO doesn't spawn a browser in CircleCI job - ui-automation

I am trying to run my E2E tests in CircleCi. Tests work locally.
On CircleCi tests are stuck after wdio's call:
[0-0] 2021-08-20T11:01:17.873Z INFO webdriver: Initiate new session using the WebDriver protocol
[0-0] 2021-08-20T11:01:17.902Z INFO webdriver: [POST] http://localhost:9515/session
[0-0] 2021-08-20T11:01:17.902Z INFO webdriver: DATA {
[0-0] capabilities: {
[0-0] alwaysMatch: {
[0-0] browserName: 'chrome',
[0-0] 'goog:chromeOptions': [Object],
[0-0] acceptInsecureCerts: true
[0-0] },
[0-0] firstMatch: [ {} ]
[0-0] },
[0-0] desiredCapabilities: {
[0-0] browserName: 'chrome',
[0-0] 'goog:chromeOptions': { args: [Array] },
[0-0] acceptInsecureCerts: true
[0-0] }
[0-0] }
Locally, after this request follows command that opens url in a browser.
But for me it throws timeout error like this:
[0-0] 2021-08-20T11:03:18.009Z WARN webdriver: Request timed out! Consider increasing the "connectionRetryTimeout" option.
Here's my CI config file:
version: 2.1
orbs:
browser-tools: circleci/browser-tools#1.2.1
jobs:
e2e:
working_directory: /tmp/circle-run
docker:
- image: cimg/node:14.16.1-browsers
resource_class: large
steps:
- browser-tools/install-chrome
- browser-tools/install-chromedriver
- checkout
- run:
name: Install Node Modules
command: npm ci
- save_cache:
key: dependency-cache-{{ .Environment.CACHE_VERSION }}-{{ checksum
"package.json" }}-{{checksum "package-lock.json" }}
paths:
- ./node_modules
- run:
name: lint
command: npm run lint
- run:
name: Run E2E tests on staging
command: npm run test:e2e
- store_test_results:
path: tests/wdio-e2e/allure-results
// ETC
I run WebdriverIO using chromedriver-service.
I don't think that problem is with access to the internet, because I tried to solve this with Selenium Standalone service and was able to curl a jar file.
What did I do wrong?

The problem was with wdio.config.js and async before() function. Forgot to remove it while was playing with setup.
async beforeTest() and async afterTest() functions can remain in the config file safely - they don't cause any trouble.

Related

Bitbucket pipeline fails with mongo service

I'm trying to setup test for my backend in Bitbucket Pipelines. But when I set jest.config with jest-mongodb the tests doesn't even start and exit with this error.
The tests are working perfectly fine on local.
Here's my pipeline configuration part that doesn't work:
image: node:18.12.0
definitions:
services:
mongo:
image: mongo
caches:
nodeall: ./node_modules
yarn: /usr/local/share/.cache/yarn
steps:
- step: &Quality-Check
name: Code Quality Checks ๐ŸŽ€
script:
- echo Fixing code quality and format ๐Ÿ”Ž
- yarn install
- yarn run lint:fix
- yarn format:fix
- step: &Testing
name: Testing ๐Ÿงช
caches:
- nodeall
script:
- yarn install
# - yarn run test
- echo Checking test coverage and generating report ๐Ÿ“œ
- yarn run test:coverage
artifacts:
- coverage/**
services:
- mongo
pipelines:
branches:
main:
- step:
name: Install dependencies
caches:
- nodeall
script:
- yarn install
- step: *Quality-Check
- step: *Testing
When i search for this error i'm headed to mongo-memory-server but i don't use this package in the code. And couldn't find anything.
I've tried changing anchors, calling mongo service earlier, changing mongo docker image but no success.
I'm expecting that the test and pipeline pass
EDIT
I tried 3 different Jest.configs and realise that the one that was on the project actually use memory-server.
Here are the 3 configs i tried
const { defaults: tsjPreset } = require('ts-jest/presets')
//Custom config with files
// module.exports = {
// preset: 'ts-jest',
// globalSetup: './mongo-memory-server/globalSetup.ts',
// globalTeardown: './mongo-memory-server/globalTeardown.ts',
// setupFilesAfterEnv: ['./mongo-memory-server/setupFile.ts'],
// }
//Config for mongo-memory-db
module.exports = {
preset: '#shelf/jest-mongodb',
transform: tsjPreset.transform,
}
// Basic config
// module.exports = {
// preset: 'ts-jest',
// testEnvironment: 'node',
// setupFiles: ['dotenv/config'],
// }

mongodb memory server Wrongfully downloading binaries on CircleCi even tho they are cached

Im using mongodb memory server.
Locally everything passes, but on circle ci it tries to download the binary even tho it's already there.
By running node node_modules/mongodb-memory-server/postinstall.js on CircleCi I see this output:
However then down the line when I run my tests it tries to download the binary again:
in addition, the SYSTEM_BINARY env variable is set to the path where the binary is.
Versions
NodeJS: v17.6.0
mongodb-memory-server-*: 8.8.0
mongoose: 6.4.7
system: ubuntu 20.04
Code Example
// .circleci.config.yml
version: 2.1
orbs:
node: circleci/node#5.0.2
jobs:
main:
docker:
- image: cimg/node:lts-browsers
steps:
- checkout
- node/install-packages:
pkg-manager: yarn
- run: echo $SYSTEM_BINARY
- run: node node_modules/mongodb-memory-server/postinstall.js
- run: yarn test:api
workflows:
build:
jobs:
- main
// mock-db-test-util.js
import { MongoMemoryServer } from "mongodb-memory-server"
import mockMongoose from "mongoose"
const mockMongoMemoryServer = MongoMemoryServer.create()
// #ts-ignore
jest.mock("../../src/db", () => ({
// #ts-ignore
...(jest.requireActual("../../src/db").default as any),
// #ts-ignore
connect: jest.fn().mockImplementation(async () => {
const mongo = await mockMongoMemoryServer
const uri = mongo.getUri()
await mockMongoose.connect(uri)
}),
}))

WebdriverIO can not create session to test Android emulator with Appium

I am using Visual Studio Code and WDIO with Appium to test Android on emulator by Android Studio, but I can not run Appium for some reason. However Android home and Java home has been set and Appium Doctor confirms necessary dependencies are completed, no fix needed.
I have tried with Appium stand-alone and from Command too.
Wit Appium standalone the ERROR log is the below:
ERROR webdriver: Request failed with status 500 due to session not created: Unable to create session from {
"desiredCapabilities": {
"platformName": "android",
"appium:deviceName": "Pixel",
"appium:platformVersion": "10.0",
"appium:app": "\u002fUsers\u002fzsolt\u002fappium_js\u002fApiDemos-debug.apk"
If I add ['appium'] to services in wdio.config.js the ERROR log is the below, though Appium stand-alone is shut:
ERROR #wdio/cli:utils: A service failed in the 'onPrepare' hook
Error: Appium exited before timeout (exit code: 2)
[HTTP] Could not start REST http interface listener. The requested port may already be in use. Please make sure there is no other instance of this server running already.
at ChildProcess.<anonymous> (C:\Users\zsolt\Documents\AppiumTestProject\node_modules\#wdio\appium-service\build\launcher.js:103:16)
at Object.onceWrapper (events.js:417:26)
at ChildProcess.emit (events.js:310:20)
at ChildProcess.EventEmitter.emit (domain.js:482:12)
at Process.ChildProcess._handle.onexit (internal/child_process.js:275:12)
This is my wdio.config.js file with using Appium stand-alone:
exports.config = {
runner: 'local',
port: 4723,
specs: [
'./test/specs/**/*.js'
],
exclude: [
// 'path/to/excluded/files'
],
maxInstances: 10,
capabilities: [{
platformName: 'android',
'appium:deviceName': 'Pixel',
'appium:platformVersion': '10.0',
'appium:app': '/Users/zsolt/appium_js/ApiDemos-debug.apk'
}],
logLevel: 'error',
bail: 0,
baseUrl: 'http://localhost',
waitforTimeout: 10000,
connectionRetryTimeout: 120000,
connectionRetryCount: 3,
services: ['selenium-standalone',
/*['appium', {
//command : 'appium'
}]*/],
reporters: ['spec'],
mochaOpts: {
ui: 'bdd',
timeout: 60000
},
These are my:
"devDependencies": {
"#wdio/local-runner": "^6.1.11",
"#wdio/mocha-framework": "^6.1.8",
"#wdio/selenium-standalone-service": "^6.0.16",
"#wdio/spec-reporter": "^6.1.9",
"#wdio/sync": "^6.1.8",
"appium": "^1.17.1"
Has anybody an idea what am I doing wrong?
Welcome to Stack-overflow!
Below is my configuration and I believe you are missing some important details.
{
platformName: 'Android',
maxInstances: 1,
'appium:deviceName': 'Device Name',
'appium:platformVersion': '8'
'appium:orientation': 'PORTRAIT',
'appium:app': 'Path to App',
'appium:automationName': 'UiAutomator2',
'appium:noReset': true,
'appium:newCommandTimeout': 240,
}
There are boilerplates from maintainers themselves here.
I have played with the boilerplates and was able to run the tests on android emulator through Appium finally.
I have then compared the differences in conf.js and figured out, the below is needed to execute the test.
services:[
[
'appium',
{
// For options see
// https://github.com/webdriverio/webdriverio/tree/master/packages/wdio-appium-service
args: {
// For arguments see
// https://github.com/webdriverio/webdriverio/tree/master/packages/wdio-appium-service
},
command: 'appium',
},
],
],
Interesting but actually the test runs with only the below capabilites too:
capabilities: [{
platformName: 'Android',
'appium:deviceName': 'Pixel 2',
'appium:app': join(process.cwd(), './ApiDemos/ApiDemos-debug.apk'),
}],
When I execute the test it logs almost the same error messages as before though at the end of the execution it runs the test on the emulator. I did not use the Appium Desktop app.
Not perfect but works...
I guess this issue has been sorted out.
Cheers
Also you need to install the Appium service:
$ npm i #wdio/appium-service --save-dev
Finally check in your wdio.conf.js:
port: 4723, // default appium port
services: [
[
'appium',
{
args: {
},
command: 'appium'
}
]
],
Check that the file you are running is inside the correct folder when you do the 'npx wdio'.
this file

How can cypress be made to work with aurelia with github actions and locally?

Ok, so I added cypress to aurelia during my configuration and it worked fine. When I went to set up cypress on github as just a command, I could not get it to recognize puppeteer as a browser. So instead I went and used the official github actions for cypress, and that works
- name: test
uses: cypress-io/github-action#v1
with:
start: yarn start
browser: ${{matrix.browser}}
record: true
env:
# pass the Dashboard record key as an environment variable
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
however I had to set my cypress.json as follows
{
"baseUrl": "http://localhost:8080",
"fixturesFolder": "test/e2e/fixtures",
"integrationFolder": "test/e2e/integration",
"pluginsFile": "test/e2e/plugins/index.js",
"screenshotsFolder": "test/e2e/screenshots",
"supportFile": "test/e2e/support/index.js",
"videosFolder": "test/e2e/videos",
"projectId": "..."
}
and now running yarn e2e doesn't work because there's no server stood up, as it's not doing it itself anymore via cypress.config.js
const CLIOptions = require( 'aurelia-cli').CLIOptions;
const aureliaConfig = require('./aurelia_project/aurelia.json');
const PORT = CLIOptions.getFlagValue('port') || aureliaConfig.platform.port;
const HOST = CLIOptions.getFlagValue('host') || aureliaConfig.platform.host;
module.exports = {
config: {
baseUrl: `http://${HOST}:${PORT}`,
fixturesFolder: 'test/e2e/fixtures',
integrationFolder: 'test/e2e/integration',
pluginsFile: 'test/e2e/plugins/index.js',
screenshotsFolder: 'test/e2e/screenshots',
supportFile: 'test/e2e/support/index.js',
videosFolder: 'test/e2e/videos'
}
};
how can I make it so that yarn e2e works as it previously did, and have it working on github?(I don't care which side of the equation is changed)
here's yarn e2e not sure what the au is doing under the hood.
"e2e": "au cypress",
Easiest way to achieve this, create a test/e2e/cypress-config.json
{
"baseUrl": "http://localhost:8080",
"fixturesFolder": "test/e2e/fixtures",
"integrationFolder": "test/e2e/integration",
"pluginsFile": "test/e2e/plugins/index.js",
"screenshotsFolder": "test/e2e/screenshots",
"supportFile": "test/e2e/support/index.js",
"videosFolder": "test/e2e/videos",
"projectId": "1234"
}
, and then setup the github action like this.
- name: test
uses: cypress-io/github-action#v1
with:
config-file: tests/e2e/cypress-config.json
start: yarn start
browser: ${{matrix.browser}}
record: true
env:
# pass the Dashboard record key as an environment variable
CYPRESS_RECORD_KEY: ${{ secrets.CYPRESS_RECORD_KEY }}
the path doesn't matter, just that you configure the same one. Just make sure it doesn't overlap with what aurelia wants.

Using a separate testing mongo database on mongo and Heroku

In my project I am using https://www.npmjs.com/package/dotenv-safe in order to declare environment variables needed for configuration. For example:
NODE_ENV=development
JWT_SECRET=xxxxxxx
JWT_EXPIRATION_MINUTES=15
MONGO_URI=mongodb://mongodb:27017/proddb
BASE_URI=http://localhost:3000/
MONGO_URI_TESTS=mongodb://mongodb:27017/testdb
PORT=3000
Then I use those files in a config file :
module.exports = {
env: process.env.NODE_ENV,
port: process.env.PORT,
jwtSecret: process.env.JWT_SECRET,
jwtExpirationInterval: process.env.JWT_EXPIRATION_MINUTES,
mongo: {
uri: process.env.NODE_ENV === 'test'
? process.env.MONGO_URI_TESTS
: process.env.MONGO_URI,
},
logs: process.env.NODE_ENV === 'production' ? 'combined' : 'dev',
};
and in my package.json file, I've got:
"scripts": {
"start": "NODE_ENV=production node ./src/index.js",
"dev": "LOG_LEVEL=debug nodemon --inspect=0.0.0.0 ./src/index.js",
"test": "NODE_ENV=test nyc --reporter=html --reporter=text mocha --timeout 20000 --recursive src/tests"
}
The problem? Everything works fine but when tests are run on Heroku (prod) , they run on the main database and not on the testdb...