Nightwatch JS doesn’t provide any out-of-the-box solution to handle shadow doms, hence we will use the document.queryselector and shadowroot web APIs.
Let’s automate a simple scenario where will use these api’s against shadow dom elements:
1. Go to https://shop.polymer-project.org/list/mens_outerwear
2. Validate the Title of the first product in the list to be Men’s Tech Shell Full-Zip
Next, we will look into our HTML DOM. To get the title of the first product we will have to traverse through 6 different elements (marked below):
For elements that have the shadow root, we will write:
1 | document.querySelector('shop-app').shadowRoot //1 |
For elements that don’t have the shadow root, we will simply write:
1 | document.querySelector('iron-pages') //2 |
So, to reach step-6, we have to traverse through some elements with shadow dom and some without. Hence, the final script will look like:
1 2 3 4 5 6 | document.querySelector('shop-app').shadowRoot //1 .querySelector('iron-pages') //2 .querySelector('shop-list').shadowRoot //3 .querySelector('ul > li:nth-child(1)') //4 .querySelector('shop-list-item').shadowRoot //5 .querySelector('.title').innerText //6 |
We will then verify this script in the browser console. It should give us the text Men’s Tech Shell Full-Zip.
Now to write the above script inside a Nightwatch test, we will use the .execute() method.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 | module.exports = { before: function (browser) { //Declaring Global Timeout browser.globals.waitForConditionTimeout = 7000 }, 'Shadow DOM in Nightwatch JS': function (browser) { browser .url('https://shop.polymer-project.org/list/mens_outerwear') .waitForElementVisible('body') .execute(function () { return document.querySelector('shop-app').shadowRoot //1 .querySelector('iron-pages') //2 .querySelector('shop-list').shadowRoot //3 .querySelector('ul > li:nth-child(1)') //4 .querySelector('shop-list-item').shadowRoot //5 .querySelector('.title').innerText //6 }, [], function (result) { this.assert.equal(result.value, 'Men\'s Tech Shell Full-Zip') }) }, after: function (browser) { browser.end() } } |
We are validating the item title as Men’s Tech Shell Full-Zip in the callback function using the command this.assert.equal(result.value, ‘Men\’s Tech Shell Full-Zip’)
After Execution:
Do check out 🙂
Github:Â https://github.com/alapanme/NightwatchJS
All Nightwatch JS Articles: https://testersdock.com/nightwatch-js-tutorial/
I am getting below error when I try to access shadow DOM element
Error while running .executeScript() protocol action: An error occurred while executing user supplied JavaScript. – javascript error: Cannot read property ‘shadowRoot’ of null
Tried to use async/await but nothing worked
Hi Bhawna, I tried executing the tests locally and it was working for me without any errors. I would suggest you create an issue on Stackoverflow with all the relevant info, as it is difficult to debug the issue with just the error message.
Here you are getting innertext, i need to click on the element inside shadow-root. Any idea how to do that