The site I'm working on is protected by a basic auth pop-up.
Before logging in the actual website I'm using the the custom command:
Cypress.Commands.add('authenticateUrl', (url, user, pass) => {
cy.visit(url, {
auth: {
username: user,
password: pass,
},
})
})
The problem is that, once I log out, the pop up is shown again but not in the automated section.
The alert pops up in the cypress browser it self (where I can't run any test!).
Any suggestion on how to handle this?
Apparently it only happes when testing on firefox.
Related
I'm trying to automate a login process for our site which uses Auth0 & Google Sign in. On the login page if you click Google sign in you get sent to an Auto0 page with a form and another Google sign in link, the page contains a URL something like:
https://OURDOMAIN.auth0.com/login?state=*REMOVED*
It's the first time I'm trying to use cy.origin() In my test I'm trying this:
cy.get("a[testid='googleSignInButton']").click()
cy.origin('https://OURDOMAIN.auth0.com/', () => {
cy.get("input[type='email']").type('anEmail#me.com')
})
The problem is whatever I try to do in the origin block just returns a timeout trying to find the element.
I've set experimentalSessionAndOrigin: true is there something I'm doing wrong? Unfortuantly the way we are using Auth0 and Google Sign in means it's not possible to do it via API calls.
try without cy.origin()
I had the same problem, and it was fixed by removing the cy.origin()
Try this one:
Cypress.Commands.add('loginSession', (email, password) => { cy.session([email, password], () => {
cy.visit('/').then(() => {
//cy.origin('auth0.com', { args: [email, password] }, ([email, password]) => {
cy.get('#username').type(email)
cy.get('#password').type(password)
cy.get("button[type='submit']").click({ force: true })
// })
})
cy.get('[data-cy="logo"]').should('be.visible')
})
});
I have a website which needs browser authentication on all page visits. If I use the below code on all page visits it works fine:
describe('WW2-3461 validate patches for contrib modules and core', () => {
it('should visit my base URL', () => {
cy.visit(Cypress.env('base_url'), {
// Add basic auth headers
auth: {
username: Cypress.env('browserAuthentication').username,
password: Cypress.env('browserAuthentication').password
},
failOnStatusCode: false
})
})
})
I am passing the base_url as an environment through CLI:
npx cypress run --spec file.spec.js --env base_url=$base_url
I don't want to use browserauthentication on all page visits, so I created a custom command like below (in integration/project/utility.js file):
Cypress.Commands.add('addBrowserAuthentication', (url) => {
cy.visit(url, {
// Add basic auth headers
auth: {
username: Cypress.env('browserAuthentication').username,
password: Cypress.env('browserAuthentication').password
},
failOnStatusCode: false
})
})
However if I call this command inside a spec file, like below:
import './utility.spec'
describe('WW2-3461 validate patches for contrib modules and core', () => {
beforeEach(() => {
cy.addBrowserAuthentication(Cypress.env('cypress_host'))
})
it('should visit my base URL', () => {
cy.visit(Cypress.env('cypress_host'), {
})
})
the browser authentication does not seem to work (tried to call it inside before() hook or directly inside the test scenario) as it returns
> 401: Unauthorized
This was considered a failure because the status code was not `2xx`.
This http request was redirected '1' time to:
- 302: https://mysite.local
If you do not want status codes to cause failures pass the option: `failOnStatusCode: false`
I can't seem to work around this issue. Tried using cy.request() but getting the same issue. Has someone faced this issue?
You don't need to pass env variable as a parameter, you can directly access it inside the custom command.
Cypress.Commands.add('addBrowserAuthentication', () => {
cy.visit(Cypress.env('base_url'), {
// Add basic auth headers
auth: {
username: Cypress.env('browserAuthentication').username,
password: Cypress.env('browserAuthentication').password,
},
failOnStatusCode: false,
})
})
And in your test directly use:
cy.addBrowserAuthentication()
Also I am not sure if its required to visit the website two times. So you can remove cy.visit(Cypress.env('cypress_host') if you are already using cy.addBrowserAuthentication().
Since this works
cy.visit(Cypress.env('base_url'), {
// Add basic auth headers
auth: {
username: Cypress.env('browserAuthentication').username,
password: Cypress.env('browserAuthentication').password
},
failOnStatusCode: false
})
but this doesn't
cy.addBrowserAuthentication(Cypress.env('cypress_host'))
it looks like Cypress.env('cypress_host') is not the same as Cypress.env('base_url').
Everything else looks good in your command, so I'd try with
cy.addBrowserAuthentication(Cypress.env('base_url'))
When you cy.visit(Cypress.env('cypress_host') without headers inside the test, the auth headers from addBrowserAuthentication are lost. I suggest removing that cy.visit().
I have a cy.visit() calls with basic authentication which looks like this:
it('launch website', () => {
cy.visit('url', {
auth: {
username: '....',
password: '....',
},
})
And it works fine. But in order to make this code more useable, I dont want to hard code my credentials in every test, but I want to create a command so every time I visit that page, it uses my basic auth. I tried to implement solutions from Adding basic auth to all requests in Cypress , but it didnt work for me. It doesnt accept credentials that are stored in command. file. Any ideas other then those already mentioned?
Many thanks :)
You can use Cypress custom commands for this.
Go to cypress/support/commands.js and wrte:
Cypress.Commands.add('authenticateUrl', (url, user, pass) => {
cy.visit(url, {
auth: {
username: user,
password: pass,
},
})
})
In your test you can just write this. You can pass url, username and passwords as parameters.
cy.authenticateUrl('https://example.com', 'admin', 'pass123')
In case you don't want to use paramters, you can directly harcode url, username and password inside the custom command.
Cypress.Commands.add('authenticateUrl', () => {
cy.visit('https://example.com', {
auth: {
username:'admin',
password:'pass123',
},
})
})
In your test just use:
it('launch website', () => {
cy.authenticateUrl() //Launch URL and authenticate
})
This can be avoided by overwriting the visit function. Add this to cypress/support/index.js
Cypress.Commands.overwrite('visit', (originalVisit, url) => {
originalVisit(url, {
auth: {
username: 'username',
password: 'password'
}
})
});
Notice that this code only working with cy.visit(url). If you pass another arguments you should change it according to your situation.
Using the Bot Framework w/ Microsoft.Bot.Builder v4.6.3
Is it possible to have users sign in only once using the web-based authentication flow, doesn't matter if they sign in via tabs or via bot conversation? If they sign in via a link from a tab, I'd like to have the bot know about this.
I have tried the following for test, omitting any security checks:
All pages are with the following js files imported:
https://statics.teams.microsoft.com/sdk/v1.4.2/js/MicrosoftTeams.min.js
https://cdnjs.cloudflare.com/ajax/libs/oidc-client/1.9.1/oidc-client.min.js
On load, the tab page executes microsoftTeams.initialize();
Add a button to the tab page:
<button onclick="authenticate()">Authenticate</button>
The authenticate function contains the following:
function authenticate() {
microsoftTeams.authentication.authenticate({
url: window.location.origin + "/tabs/tabAuthStart",
width: 600,
height: 535,
successCallback: function (result) {
// The debug function just displays what's sent to it using document.write()
debug(result);
},
failureCallback: function (reason) {
debug(reason);
}
});
}
The tabAuthStart page contains the following script which is executed on page load:
microsoftTeams.initialize();
const mgr = new Oidc.UserManager({
userStore: new Oidc.WebStorageStateStore(),
authority: '<my-identity-server>',
client_id: '<my-id-srv-client>',
redirect_uri: window.location.origin + '/tabs/tabAuthCallback',
response_type: 'id_token token',
scope: '<my-requested-scopes>',
accessTokenExpiringNotificationTime: 10,
automaticSilentRenew: true,
filterProtocolClaims: true,
loadUserInfo: true
});
mgr.signinRedirect();
After a successful sign in at the identity provider, I'm redirected back to /tabs/tabAuthCallback
On load, the /tabs/tabAuthCallback executes the following code:
microsoftTeams.initialize();
var mgr = new Oidc.UserManager({ userStore: new Oidc.WebStorageStateStore(), loadUserInfo: true, filterProtocolClaims: true });
mgr.signinRedirectCallback().then(function (user) {
// I expected something involving a bot to happen after calling this
microsoftTeams.authentication.notifySuccess({
idToken: user.id_token,
accessToken: user.access_token,
tokenType: user.token_type,
expiresIn: user.expires_at
})
}).catch(function (err) {
microsoftTeams.authentication.notifyFailure("UnexpectedFailure: " + err);
});
The pop-up window is closed and the successCallback function from the tab is executed successfully with the user information that I have sent. However, the bot is not in any way notified about this (as far as I know). I have set a breakpoint in the bot controller action resolved by POST /api/messages but it's never hit.
Do I need to handle this manually? I.e. pass the user info to the back-end? But even if so, how do I know which Teams user to associate this user info (i.e. access token) to?
If this is possible to do in a reliable and secure way, would it also be possible in the opposite direction, i.e. having the user token available to the tab if they have already been authenticated from a bot conversation or a messaging extension? Is there a reliable way to identify a Teams user who's navigating tabs, in order to obtain their access token from the back-end, assuming the back-end already obtained them via the authentication mechanism?
I have developed a PWA application with google and microsoft oauth login integration.Now I want the PWA application to run as windows PWA app in windows mobile and desktop applications, so I tried registering the app using AppX as stated in the following link, https://blogs.windows.com/msedgedev/2018/02/06/welcoming-progressive-web-apps-edge-windows-10/#R6xvoOyZeLza5oGW.97
and ran the application in development mode using PowerShell in windows 10 OS version, the microsoft login works great, However when I try to login using google the application starts loading and exits after some time.[the popup to show the login window also doesn't come up].
Could anyone throw a light on what's happening ?.I researched but I couldn't get any solutions.
Edit
The following API is used for login with google, in the client[react]
gapi.load('auth2', () => {
this.auth2 = gapi.auth2.init({
client_id: constant.CLIENT_ID,
cookie_policy: 'single_host_origin',
scope: constant.SCOPE,
});
});
loginWithGoogle = () => {
const options = {
scope: constant.SCOPE,
};
options.prompt = 'select_account';
this.provider = 'google';
this.auth2.grantOfflineAccess(options).then((data) => {
this.loginUser(data.code);
});
}
Maybe is because your browser´s popup blocker, anyway you could use redirection instead popup mode, using ux_mode option (you have to configure the redirection url on OAuth 2.0 client IDs options)
gapi.load('auth2', () => {
this.auth2 = gapi.auth2.init({
ux_mode: 'redirect',
client_id: constant.CLIENT_ID,
cookie_policy: 'single_host_origin',
scope: constant.SCOPE,
});
});