Skip to content

Instantly share code, notes, and snippets.

@ng-marcus
Created October 9, 2019 13:10
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ng-marcus/79f5c28b4be242520c4b5e2f9ee21c58 to your computer and use it in GitHub Desktop.
Save ng-marcus/79f5c28b4be242520c4b5e2f9ee21c58 to your computer and use it in GitHub Desktop.
Authenticating to Office 365 SSO with Cypress
/// <reference types="Cypress" />
const xml = `<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope"
xmlns:a="http://www.w3.org/2005/08/addressing"
xmlns:u="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd">
<s:Header>
<a:Action s:mustUnderstand="1">http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue</a:Action>
<a:ReplyTo>
<a:Address>http://www.w3.org/2005/08/addressing/anonymous</a:Address>
</a:ReplyTo>
<a:To s:mustUnderstand="1">https://login.microsoftonline.com/extSTS.srf</a:To>
<o:Security s:mustUnderstand="1"
xmlns:o="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
<o:UsernameToken>
<o:Username>${Cypress.env('USERNAME')}</o:Username>
<o:Password>${Cypress.env('PASSWORD')}</o:Password>
</o:UsernameToken>
</o:Security>
</s:Header>
<s:Body>
<t:RequestSecurityToken xmlns:t="http://schemas.xmlsoap.org/ws/2005/02/trust">
<wsp:AppliesTo xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<a:EndpointReference>
<a:Address>https://${Cypress.env('TENANT')}.sharepoint.com/</a:Address>
</a:EndpointReference>
</wsp:AppliesTo>
<t:KeyType>http://schemas.xmlsoap.org/ws/2005/05/identity/NoProofKey</t:KeyType>
<t:RequestType>http://schemas.xmlsoap.org/ws/2005/02/trust/Issue</t:RequestType>
<t:TokenType>urn:oasis:names:tc:SAML:1.0:assertion</t:TokenType>
</t:RequestSecurityToken>
</s:Body>
</s:Envelope>`
const headers = {
Authorization: ""
};
const xmlHeaders = {} // { 'Content-Type', 'application/xml'}
const cookieHeaders = {
Host: `${Cypress.env('TENANT')}.sharepoint.com`
}
describe('Logging In - Single Sign on', function () {
Cypress.Commands.add('loginBySingleSignOn', (overrides = {}) => {
Cypress.log({
name: 'loginBySingleSignOn'
})
cy.request({
method: 'POST',
url: `https://login.microsoftonline.com/${Cypress.env('TENANT')}.onmicrosoft.com/oauth2/v2.0/token`,
form: true,
body: {
client_secret: Cypress.env('CLIENT_SECRET'),
grant_type: 'client_credentials',
scope: 'https://graph.microsoft.com/.default',
client_id: Cypress.env('CLIENT_ID'),
},
}).then(response => {
cy.log("response from login")
cy.log(response)
headers.Authorization = `Bearer ${response.body.access_token}`;
cy.log(xml)
cy.request({
method: 'POST',
url: 'https://login.microsoftonline.com/extSTS.srf',
headers: xmlHeaders,
form: false,
body: xml,
}).then(xmlresponse => {
cy.log(xmlresponse.body)
var oParser = new DOMParser();
var oDOM = oParser.parseFromString(xmlresponse.body, "application/xml");
cy.log(oDOM);
var tokens = oDOM.getElementsByTagName('wsse:BinarySecurityToken')
cy.log(tokens);
const magicString = tokens[0].innerHTML;
cy.log(magicString)
cy.request({
method: 'POST',
url: `https://${Cypress.env('TENANT')}.sharepoint.com/_forms/default.aspx?wa=wsignin1.0`,
headers: cookieHeaders,
form: false,
body: magicString,
}).then(cookieResponse => {
cy.log(cookieResponse)
})
})
})
})
})
describe('Login to O365', () => {
before(function () {
cy.loginBySingleSignOn()
.then(
resp => {
cy.log("Ready to call SPO")
}
)
})
it('opens page as logged in user', () => {
cy.log(headers);
cy.visit('/sites/mysite')
})
})
@kamiloski88
Copy link

Hi, how you get this client_secret? Is it static or generated before/after login?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment