Using require with relative paths Using require with relative paths angularjs angularjs

Using require with relative paths


I had the same problem and I ended up with the following solution.In my Protractor config file I have a variable which stores a path to a base folder of my e2e tests. Also, Protractor config provides the onPrepare callback, where you can use a variable called global to create global variables for your tests. You define them as a properties of that global variable and use the same way you use globals browser or element in tests. I've used it to create custom global require functions to load different types of entities:

// __dirname retuns a path of this particular config file// assuming that protractor.conf.js is in the root of the projectvar basePath = __dirname + '/test/e2e/';// /path/to/project/test/e2e/exports.config = {    onPrepare: function () {        // "relativePath" - path, relative to "basePath" variable        // If your entity files have suffixes - you can also keep them here        // not to mention them in test files every time        global.requirePO = function (relativePath) {            return require(basePath + 'po/' + relativePath + '.po.js');        };        global.requireHelper = function (relativePath) {            return require(basePath + 'helpers/' + relativePath + '.js');        };    }};

And then you can use these global utility methods in your test files right away:

"use strict";    var localStorageHelper = requireHelper('localStorage');// /path/to/project/test/e2e/helpers/localStorage.js var loginPage = requirePO('login');// /path/to/project/test/e2e/po/login.po.jsvar productShowPage = requirePO('product/show');// /path/to/project/test/e2e/po/product/show.po.jsdescribe("Login functionality", function () {    beforeEach(function () {        browser.get("/#login");        localStorageHelper.clear();    });    // ...});


We've been facing the same issue and decided to turn all page object and helper files into node packages. Requiring them in tests is now as easy as var Header = require('header-po'). Another benefit of converting to packages is that you can use proper versioning.

Here is a simple example:

./page-objects/header-po/index.js

//page-objects/header-po/index.js'use strict';var Header = function () {    this.goHome = function () {        $('#logo a').click();    };  };module.exports = Header;

./page-objects/header-po/package.json

{    "name": "header-po",    "version": "0.1.1",    "description": "Header page object",    "main": "index.js",    "dependencies": {}}

./package.json

{    "name": "e2e-test-framework",    "version": "0.1.0",    "description": "Test framework",    "dependencies": {        "jasmine": "^2.1.1",        "header-po": "./page-objects/header-po/",    }}

./tests/header-test.js

'use strict';var Header = require('header-po');var header = new Header();describe('Header Test', function () {    it('clicking logo in header bar should open homepage', function () {        browser.get(browser.baseUrl + '/testpage');        header.goHome();        expect(browser.getCurrentUrl()).toBe(browser.baseUrl);    });});


I have had the same issue. Did similar solution to Michael Radionov's, but not setting a global function, but setting a property to protractor itself.

protractor.conf.js

onPrepare: function() {  protractor.basePath = __dirname;}

test-e2e.js

require(protractor.basePath+'/helpers.js');describe('test', function() {   .......});