I have a test broken into 3 ponents. The main page object Page, the page in question HomePage and the test itself.
I want HomePage
to extend the Page
object. However what I found is - if in the Page class I use:
module.exports = new Page()
I get the error ERROR: Class extends value #<Page> is not a function or null
however if i use
module.exports = Page
it works perfectly.
Could someone please explain why this is so? Is it because the Page object itself is only constructed with each of the pages its the parent of, e.g. HomePage
or LoginPage
or whatever other page?
class Page {
constructor() {
this.title = 'My Page';
}
open(path) {
browser.url('/' + path);
}
}
module.exports = Page;
==
var Page = require('../page-models/Page');
class HomePage extends Page {
get username() { return browser.element('#username'); }
open() {
super.open('');
}
}
module.exports = new HomePage();
== The test itself
var HomePage = require('../page-models/home.page');
describe('Something great', function(){
it('tests this', function(){
HomePage.open();
...
Any help appreciated. p.s. using nodejs, webdriverio, mocha and chai.
I have a test broken into 3 ponents. The main page object Page, the page in question HomePage and the test itself.
I want HomePage
to extend the Page
object. However what I found is - if in the Page class I use:
module.exports = new Page()
I get the error ERROR: Class extends value #<Page> is not a function or null
however if i use
module.exports = Page
it works perfectly.
Could someone please explain why this is so? Is it because the Page object itself is only constructed with each of the pages its the parent of, e.g. HomePage
or LoginPage
or whatever other page?
class Page {
constructor() {
this.title = 'My Page';
}
open(path) {
browser.url('/' + path);
}
}
module.exports = Page;
==
var Page = require('../page-models/Page');
class HomePage extends Page {
get username() { return browser.element('#username'); }
open() {
super.open('');
}
}
module.exports = new HomePage();
== The test itself
var HomePage = require('../page-models/home.page');
describe('Something great', function(){
it('tests this', function(){
HomePage.open();
...
Any help appreciated. p.s. using nodejs, webdriverio, mocha and chai.
Share edited Jul 25, 2017 at 7:11 userMod2 asked Jul 25, 2017 at 6:58 userMod2userMod2 9,00217 gold badges73 silver badges134 bronze badges1 Answer
Reset to default 8When you write:
var Page = require('../page-models/Page');
The variable Page
is whatever you exported from '../page-models/Page' with module.exports
. If you export a new Page()
object then your variable Page
will be that instance of the Page
class you created with new
not the class itself. And you can't extend
an instance. Also,require()
caches it's results so you always get the same object.
As you have it with module.exports = Page
you export the class and anyone require
-ing it is free to create their own instances as they see fit.
I know you didn't ask, but one thing to think about is creating a uniform interface with your classes. If you are going to export the Page
class and ask users to instantiate or extend that class, you should consider doing the same for Homepage
. Perhaps you might want to do something like:
var Homepage = require('../page-models/home.');
class MobileHomePage extends Homepage {
//...
}
You can't do that it you export an instance with new HomePage()
. This means you would need to create the instance in your test with something like:
var HomePageClass = require('../page-models/home.page');
var Homepage = new HomePageClass()
which is more verbose, but also makes your modules more flexible.