It is absolutely correct to go ahead with the isVisible method. You may know that in the callback you can check the result.value property to see whether or not the element was visible, i.e:
browser.isVisible('#advanced-search', results => {
if (results.value) { /* is visible */ }
else { /* is not visible */ }
});
Alternatively, you could call the selenium API .elements command and then check the result array's length like the following:
browser.elements('css selector', '#advanced-search', results => {
if (results.value.length > 0) { /* if the length of the resultant array is greater than 0, which means an element exists */ }
else { /* element does not exist */ }
});
This, in fact, could be wrapped into a custom command:
// isPresent.js
module.exports.command = function (selector, callback) {
return this.elements('css selector', selector, results => {
if (results.status !== 0) { // only when some error occurs, this will handle accordingly
}
callback(results.value.length > 0);
});
};
//If there are no errors then the call will be made like this:
browser.isPresent('#advanced-search', advancedSearchPresent => {
// make decisions here
}
If you are going to be making additional API calls in the callback, it may be wise to wrap it all in a .perform call:
browser.perform((_, done) => {
browser.isPresent('#advanced-search', advancedSearchPresent => {
// ...do more stuff...
done();
});
});
As to why the .perform is necessary, this might be helpful.