protractor test timed out on Chrome but not on FF - protractor

I'm running a protractor test.
there is a login part which is not Angular and then the home page which is Angular part.
after passing the login part - on Chrome I get a Timeout, but on FF it continues successfully.
it used to run also on Chrome before, and a friend using Robot Framework doesn't get to timeout even when using chrome.
error message:
timeout: timed out after 30000 msec waiting for spec to complete
I've tries also adding
defaultTimeoutInterval: 360000
but it didn't help. it's just keep waiting.
config.js:
exports.config = {
seleniumAddress: 'http://localhost:4444/wd/hub',
capabilities: {
'browserName': 'chrome'
// 'browserName': 'firefox'
},
specs: ['*/loginEAPTest.js'],
params: {
login: {
user: '****',
password: '****'
}
},
resultJsonOutputFile: 'TestResults/Test.js',
jasmineNodeOpts: {
isVerbose: true,
showColors: true,
//defaultTimeoutInterval: 360000,
includeStackTrace: true
},
onPrepare: function() {
// for non-angular page
browser.ignoreSynchronization = true;
}
};
loginEAPTest.js:
var LoginPage = require('../global/LoginPage');
var capture = require('../global/screenshots');
describe('login Testing', function () {
var login = new LoginPage();
beforeEach(function(){
login.get();
login.justClickLogin();
}
);
it('Should login using Email & Password', function () {
browser.sleep(10000);
browser.driver.findElement(by.id('userName_str')).sendKeys ("****");
browser.driver.findElement(by.id('password')).sendKeys("******");
browser.driver.findElement(by.xpath("//input[contains(#value,'Log In')]")).click();
browser.ignoreSynchronization = false;
browser.sleep(5000);
browser.switchTo().defaultContent();
expect(element(by.css('[data-ui-sref=myApps]')).isDisplayed()).toBe(true);
});
});
LoginPage.js (relevant part):
this.justClickLogin = function() {
var loginObj = this;
loginObj.signInButton.click().then(function () {
console.log("press login");
var loginframe = element(by.tagName('iframe'));
console.log("before switch");
browser.switchTo().frame(0);
console.log("after switch");
browser.sleep(4000);
});
};
thanks.

Related

Create mongoDB Session with Socket.io connection only

I need to create a session on MongoDB when the socket connection start, I have the following code:
var express = require('express');
var session = require('express-session');
var sharedsession = require("express-socket.io-session");
var MongoDBStore = require('connect-mongodb-session')(session);
var app = express();
var http = require('http').createServer(app);
var io = require('socket.io')(http);
var store = new MongoDBStore({
uri: 'CONNECTION TO MONGODB',
collection: 'sessions',
connectionOptions: {
useNewUrlParser: true
}
});
// Catch errors
store.on('error', function(error) {
console.log(error);
});
let sessionConfig = require('express-session')({
secret: 'This is a secret',
cookie: {
maxAge: 1000 * 60 * 60 * 24 * 7 // 1 week
},
store: store,
httpOnly: false,
resave: true,
saveUninitialized: true
});
app.use(sessionConfig);
io.use(sharedsession(sessionConfig, {
autoSave:true
}));
app.get('/', function(req, res) {
res.send('<html><head><script src="http://localhost:3001/socket.io/socket.io.js"></script><script>var socket = io();</script></head><body>Test</body></html>');
});
io.on('connection', (socket) => {
console.log('a user connected');
console.log('socket.handshake',socket.handshake.session);
console.log(socket.handshake.xdomain);
console.log("A USER LOGGED IN WITH ID: ", socket.request.user);
// Accept a login event with user's data
socket.on("login", function(userdata) {
socket.handshake.session.userdata = userdata;
socket.handshake.session.save();
});
socket.on("logout", function(userdata) {
if (socket.handshake.session.userdata) {
delete socket.handshake.session.userdata;
socket.handshake.session.save();
}
});
});
http.listen(3001, () => {
console.log('listening on *:3000');
});
server = app.listen(3000);
If I access to , the session is created successfully in MongoDB, I understand that the configuration with express is ok, and the Socket Share that session correctly when I try to connect from the same domain.
The problem is, that I have a mobile app with ionic v4, that only access from a socket connection and the session is never created on MongoDB.
Any thoughts?
UPDATE 1:
I try to add passport.socketio to get a proper way to add authentication to my app, and the output of this code, is Not Session found, its right, the socket connection never add the session to the MongoDB:
var express = require('express');
var session = require('express-session');
var sharedsession = require("express-socket.io-session");
let passport = require('passport');
let passportSocketIo = require("passport.socketio");
let cors = require('cors')
var MongoDBStore = require('connect-mongodb-session')(session);
var app = express();
var http = require('http').createServer(app);
var io = require('socket.io')(http);
var store = new MongoDBStore({
uri: 'MONGO DB STRING CONNECTION',
collection: 'sessions',
connectionOptions: {
useNewUrlParser: true
}
});
// Catch errors
store.on('error', function(error) {
console.log(error);
});
app.use(cors());
app.use(passport.initialize());
app.use(passport.session());
let config = {
passport : passport,
secret: 'This is a secret',
cookie: {
maxAge: 1000 * 60 * 60 * 24 * 7 // 1 week
},
store: store,
httpOnly: false,
resave: true,
saveUninitialized: true,
success: onAuthorizeSuccess, // *optional* callback on success - read more below
fail: onAuthorizeFail
};
let sessionConfig = require('express-session')(config);
app.use(sessionConfig);
io.origins('*:*');
io.use(sharedsession(sessionConfig, passportSocketIo.authorize(config)));
app.get('/', function(req, res) {
res.send('<html><head><script src="http://localhost:3001/socket.io/socket.io.js"></script><script>var socket = io();</script></head><body>Test</body></html>');
});
io.on('connection', (socket) => {
console.log('a user connected');
console.log('socket.handshake',socket.handshake.session);
console.log(socket.handshake.xdomain);
console.log("A USER LOGGED IN WITH ID: ", socket.request.user);
// Accept a login event with user's data
socket.on("login", function(userdata) {
socket.handshake.session.userdata = userdata;
socket.handshake.session.save();
});
socket.on("logout", function(userdata) {
if (socket.handshake.session.userdata) {
delete socket.handshake.session.userdata;
socket.handshake.session.save();
}
});
});
http.listen(3001, () => {
console.log('listening on *:3000');
});
server = app.listen(3000);
function onAuthorizeSuccess(data, accept){
console.log('successful connection to socket.io');
// accept(); //Let the user through
}
function onAuthorizeFail(data, message, error, accept){
console.log("Errror",error);
if(error) accept(new Error(message));
console.log('failed connection to socket.io:', message);
// accept(null, false);
}
Try
//Before io.on('connection....
io​.​engine​.​generateId​ ​=​ (​req​) ​=>​ {
//Try to get the cookie out from
//req.rawHeaders and return it
//so the socket ID will equal to the session Id
});
//The connection event
​io​.​on​(​'​connection​'​, ​socket​ ​=>​ { ....
//You can then do a mongoose search query using the socket Id here to match the user in the db

protractor is not capturing the Screenshot with Cucumber Reporter

i am using Protractor with Cucumber to test angular application, for reporting i am using "cucumber-html-reporter", i am not able to capture the screenshot in report and its not getting saved in the given folder as well
reporter.js
const reporter = require("cucumber-html-reporter");
cucumberReporteroptions = {
theme: "bootstrap",
//jsonFile: targetJson,
jsonDir: targetjsonDir,
output: htmlReports + "/cucumber_reporter"+datetime+".html",
reportSuiteAsScenarios: true,
storeScreenshots:true,
screenshotsDirectory:htmlReports +'/screenshots',
reportSuiteAsScenarios:true,
launchReport:true,
ignoreBadJsonFile:true
};
class Reporter {
static createHTMLReport() {
try {
reporter.generate(cucumberReporteroptions); //invoke cucumber-html-reporter
} catch (err) {
if (err) {
console.log("Failed to save cucumber test results to json file.");
console.log(err);
}
}
}
hooks.js
After(function(scenario) {
const attach = this.attach;
return browser.takeScreenshot().then(function(png) {
const decodedImage = new Buffer(png, "base64");
return attach(decodedImage, "image/png");
});
});
Quick checks that you can do from your side, to make sure reporter is invoked properly:
onPrepare: () => {
browser.ignoreSynchronization = true;
browser.manage().window().maximize();
Reporter.createDirectory(jsonReports);
},
cucumberOpts: {
compiler: "ts:ts-node/register",
format: "json:./reports/json/cucumber_report.json",
require: ["../../typeScript/stepdefinitions/*.js", "../../typeScript/support/*.js"],
strict: true,
},
onComplete: () => {
Reporter.createHTMLReport();
},
Can you try this,
defineSupportCode(({After}) => {
After(function(scenario) {
if (scenario.isFailed()) {
var attach = this.attach;
return browser.takeScreenshot().then(function(png) {
var decodedImage = new Buffer(png, "base64");
return attach(decodedImage, "image/png");
});
}
});
});
Lemme know how it goes!

Test Report is not generating using 'protractor-angular-screenshot-reporter'

I am using POM concepts and all the instructions given :
https://npm.runkit.com/protractor-angular-screenshot-reporter
https://github.com/bcole/protractor-angular-screenshot-reporter/blob/master/README.md
but still no reports is generating. Is that anything I am lacking. Earlier I have used 'protractor-jasmine2-html-reporter' and it was working fine.
Console output I am getting is correct on running protractor conf.js using cmd:
4 specs, 3 failures
Finished in 32.847 seconds
[11:32:40] I/local - Shutting down selenium standalone server.
[11:32:40] I/launcher - 0 instance(s) of WebDriver still running
[11:32:40] I/launcher - chrome #01 failed 3 test(s)
[11:32:40] I/launcher - overall: 3 failed spec(s)
[11:32:40] E/launcher - Process exited with error code 1
Project Structure:
Project Structure
pages/AllevaHome.js
var AllevaHomePage = function() {
var logoutBtn = element(by.className('logoutbtn'));
this.isLogoutDisplays = function(){
var flag = logoutBtn.isDisplayed();
return flag
};
this.logout = function(){
logoutBtn.click();
};
};
module.exports = new AllevaHomePage();
pages/AllevaLogin.js
var AllevaLoginPage = function() {
var username = element(by.model('LoginViewModel.UserName'));<br>
var password = element(by.model('LoginViewModel.Password'));<br>
var loginBtn = element(by.className('orange-btn login_btn'));<br>
var securityAns = element(by.model('twoFactorModel.answer'));<br>
var proceedBtn = element(by.css('[value="Proceed"]'));<br>
this.get = function() {
browser.get('some url');
browser.manage().window().maximize();
};
function setUsername(user){
username.sendKeys(user);
};
function setPassword(pass){
password.sendKeys(pass);
};
function setAnswer(ans){
securityAns.sendKeys(ans);
};
this.login = function(user, pass, ans){
setUsername(user);
setPassword(pass);
loginBtn.click();
setAnswer(ans);
proceedBtn.click();
};
/* this.getGreetingText = function() {
return greeting.getText();
};*/
};
module.exports = new AllevaLoginPage();
testdata/LoginData.js
'use strict';
module.exports = {
LoginData: {
'Valid Username/Password': {username: 'someuser', password: 'somepass',
answer: 'someans'},
'Invalid Username/Correct Password': {username: 'testuser', password:
'Test#12345', answer: 'kusum'},
'Invalid Username/Invalid Password': {username: 'testuser', password:
'Test#1234', answer: 'kusum'},
'Valid Username/Invalid Password': {username: 'rohitnegi', password:
'Test#1234', answer: 'kusum'}
}
}
tests/AllevaLoginTest.js
var AllevaLoginObj = require('../pages/AllevaLogin.js');
var AllevaHomeObj = require('../pages/AllevaHome.js');
var LoginData = require('../testdata/LoginData.js');
var using = require('jasmine-data-provider');
describe('Checking Alleva Login Functionality', function() {
using(LoginData.LoginData, function(data, description) {
it('Login with: '+description, function() {
AllevaLoginObj.get();
AllevaLoginObj.login(data.username, data.password, data.answer);
expect(AllevaHomeObj.isLogoutDisplays());
})
});
afterEach(function() {
AllevaHomeObj.logout();
})
});
Conf.js:
var HtmlReporter = require('protractor-angular-screenshot-reporter');
exports.config = {
seleniumAddress: 'http://localhost:4444/wd/hub',
specs: [
'./tests/AllevaLoginTest.js'
],
capabilities: {
'browserName': 'chrome'
},
onPrepare: function() {
jasmine.getEnv().addReporter(new HtmlReporter({
baseDirectory: '/tmp/screenshots'
}).getJasmine2Reporter());
},
jasmineNodeOpts: {
onComplete: null,
isVerbose: true,
showColors: true,
includeStackTrace: true,
defaultTimeoutInterval: 2500000
}
};
Please let me know if you need anything else.

Protractor-Jasmine2-HTML-Report

I am working on report execution part in Protractor and using Jasmine2 Html Reporter. I am able to generate a report but when my test passes completely without any failure still report shows status as 0.00%. I am not sure why this is happening. I am also attaching the snap shot for the reference.
The code is :
var HtmlReporter = require('protractor-jasmine2-html-reporter');
var reporter = new HtmlReporter({
plugins: [{
package: 'jasmine2-protractor-utils',
showSummary: true,
reportTitle: "Clinicare Report",
filename: 'Clinicarereport.html',
disableHTMLReport: false,//disableHTMLReport
disableScreenshot: false,
captureOnlyFailedSpecs: true,
screenshotPath:'./reports/screenshots',
screenshotOnExpectFailure:true,
screenshotOnSpecFailure:true,
dest: 'protractor-reports',
filename: 'protractor-report.html',
takeScreenshots: true,
ignoreSkippedSpecs: true,
takeScreenshotsOnlyOnFailures: true
// screenshotsFolder: 'F:\\Screeshots'
}]
});
exports.config =
{
directconnect: true,
capabilities: {'browserName': 'chrome'},
framework: 'jasmine',
specs: ['example1.js'],
jasmineNodeOpts: {
defaultTimeoutInterval: 300000
},
onPrepare: function() {
// Add a screenshot reporter and store screenshots to `/tmp/screenshots`:
jasmine.getEnv().addReporter(reporter);
}
}
The spec code is:
var Excel = require('exceljs');
var XLSX = require('xlsx');
var os = require('os');
var TEMP_DIR = os.tmpdir();
var wrkbook = new Excel.Workbook();
describe('Open the clinicare website by logging into the site', function () {
it('Should Add a text in username and password fields and hit login button', function () {
console.log("hello6");
var wb = XLSX.readFile('E:\\Demo\\Generate a test report\\Data_Login.xlsx');
var ws = wb.Sheets.Sheet1;
var json = XLSX.utils.sheet_to_json(wb.Sheets.Sheet1);
console.log("json", json);
//var json = XLSX.utils.sheet_to_json(wb.Sheets.Sheet1);
//console.log("json", json);
for(var a = 0; a < json.length ; a++){
console.log("Test_URL", json[a].Test_URL);
console.log("User_Name", json[a].User_Name);
console.log("Password", json[a].Password);
browser.get(json[a].Test_URL);
//Perform Login:UserName
element(by.model('accessCode')).sendKeys(json[a].User_Name);
//Perform Login:Password
element(by.model('password')).sendKeys(json[a].Password);
//Perform Login:LoginButton
element(by.css('.btn.btn-primary.pull-right')).click();
//Clicking on New Tab
element(by.xpath('/html/body/div[3]/div[1]/div[17]/div/div/table[2]/thead/tr/th[1]/i')).click();
//Clicking on Image for Logout
element(by.css('.user-auth-img.img-circle')).click();
browser.driver.sleep(2000)
//Clicking on LogOut Button
element(by.xpath('/html/body/div[3]/div[1]/div[16]/div[1]/div/div[2]/nav/div[2]/ul/li[4]/ul/li[5]/a/span')).click();
browser.driver.sleep(2000)
//Clicking on Ok for confirmation
element(by.id('logout')).click();
console.log(json[a].User_Name + "Passed the Test");
};
})
});
Try with below spec file it's working fine.
Results you can see
describe("basic test", function () {
beforeAll(function () {
console.log('beforeAll');
});
beforeEach(function () {
console.log('beforeEach');
});
afterAll(function () {
console.log('afterAll');
});
afterEach(function () {
console.log('afterEach');
});
it("Test Case 1: to verify see the global functions hierarchy", function () {
console.log('Sample Test 1');
});
it("Test Case 2: to verify see the global functions hierarchy", function () {
browser.get('http://www.angularjs.org');
element(by.model('todoText')).sendKeys('write a protractor test');
element(by.css('[value="add"]')).click();
var todoList = element.all(by.repeater('todo in todos'));
expect(todoList.count()).toEqual(3);
});
it('should greet the named user', function() {
browser.get('http://www.angularjs.org');
element(by.model('yourName')).sendKeys('Julie');
var greeting = element(by.binding('yourName'));
expect(greeting.getText()).toEqual('Hello Julie!');
});
});

Protractor/Jasmine send REST Call when a test failed

I am using Protractor and Jasmine to test my hybrid mobile app, which works fine. I'd like to create an incident on my Team Foundation Server (TFS), when a test fails. Therefore, I have to send an REST-Call to the Api, which also works fine in my Angular App. But it does not work, when I am inside my test environment.
My Code:
var BrowsePage = require('./browse.page');
var tfsIncident = require('./tfsIncident_service');
var request = require('request');
describe('Testing the browse state', function () {
var browsePage = new BrowsePage();
var specsArray = [];
var reporterCurrentSpec = {
specDone: function (result) {
if (result.status === 'failed') {
var mappedResult = tfsIncident.create(result);
console.log(mappedResult); //This works so far, but then it crashes
var options = {
method: 'PATCH', //THis Method requiered the API
url: 'MY_COOL_API_ENDPOINT',
headers: {
'Authorization': 'Basic ' + btoa('USERNAME' + ':' + 'PASSWORD'),
'Content-Type': 'application/json-patch+json'
},
body: mappedResult
};
function callback(error, response, body) {
if (!error && response.statusCode == 200) {
var info = JSON.parse(body);
console.log(response);
console.log(info);
}
}
request(options, callback);
}
}
};
jasmine.getEnv().addReporter(reporterCurrentSpec);
//This test passes
it('should be able to take display the heading', function () {
expect(browsePage.headline.isPresent()).toBe(true);
});
// Test is supposed to fail
it('should be able to fail', function () {
expect(browsePage.headline).toBe(1);
});
// Test is supposed to fail as well
it('should be able to fail too', function () {
expect(browsePage.headline).toBe(2);
});
});
So the problem is, that my only console output is (after the console.log(mappedResult)): E/launcher - BUG: launcher exited with 1 tasks remaining
So I have no idea, why this does not work.
Any help appreciated.
Edit
Protractor: 5.0.0
Appium Desktop Client: 1.4.16.1
Chromedriver: 2.27
Windows 10 64 Bit
Jasmine: 2.4.1
I finally got my problem solved. The problem was caused by ignoring the promises by jasmine. I had to add a .controllFlow().wait() to my protractor.promise
The following code works fine:
var BrowsePage = require('./browse.page');
describe('Testing the browse state', function () {
var browsePage = new BrowsePage();
var reporterCurrentSpec = {
specDone: function (result) {
if (result.status === 'failed') {
//Mapping of the result
var incident = [
{
op: 'add',
path: '/fields/System.Title',
value: 'Test: ' + result.fullName + ' failed'
},
{
op: 'add',
path: '/fields/System.Description',
value: result.failedExpectations[0].message
},
{
op: 'add',
path: '/fields/Microsoft.VSTS.Common.Priority',
value: '1'
},
{
op: 'add',
path: '/fields/System.AssignedTo',
value: 'Name Lastname <e#mail.com>'
}
];
protractor.promise.controlFlow().wait(create(incident)).then(function (done) { //The magic happens in this line
console.log("test done from specDone:" + done);
});
}
}
};
jasmine.getEnv().addReporter(reporterCurrentSpec); //Add new Jasmine-Reporter
function create(incident) {
var request = require('request');
var defer = protractor.promise.defer(); //new promise
request({
url: 'https://MY_COOL_ENDPOINT.COM',
method: "PATCH",
json: true, // <--Very important!!!
headers: {
'Authorization': 'Basic ' + new Buffer('USERNAME' + ':' + 'PASSWORD').toString('base64'),
'Content-Type': 'application/json-patch+json'
},
body: incident
}, function (error, response, body) {
console.log(error);
console.log(response.statusCode);
console.log(body.id); //Id of created incident on TFS
defer.fulfill({
statusCode: response.statusCode
}); //resolve the promise
});
return defer.promise; //return promise here
}
it('should be able to display the heading', function () {
expect(browsePage.headline.isPresent()).toBe(true);
});
it('should be able to fail', function () {
expect(browsePage.headline.isPresent()).toBe(false);
});
it('should be able to fail 2', function () {
expect(browsePage.headline.isPresent()).toBe(false);
});
});
Attention
When the test suite is done and the last promise is not resolved at this moment, the last incident is not created. I'll try to work around by adding to the last test a browser.sleep(5000); so that the create(incident) function gets more time to finish.
Thanks to this StackOverflow answer for helping me.