Showing posts with label AngularJs. Show all posts
Showing posts with label AngularJs. Show all posts

Monday, 26 June 2017

This week 12/2017

In this post I'd like to present handy pattern which is used to selenium test called "PageObject". Truly, it is a facade pattern which hides technical aspects of html and javascript content and shares only business friendly API.
Example PageObject bellow:


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
@PageObject
public class PtfPageObject {

    private static final String MENU_SECTION = "//table[@ng-controller='AppController']";

    @FindBy(xpath = MENU_SECTION + "//tr[@id='summarize']/td[8]/span")
    private WebElement profitAmount;

    @Autowired
    private WebDriver webDriver;

    public String findProfitAmount(){
        TimeoutUtils.waitForAngularJS(webDriver);
        return profitAmount.getText();
    }
}

I have turned this topic up after a half year. That time I used it to test web pages supported by JSP, ZK Framework or AngularJS pages and I found solution to synchronize an asynchronously loaded content.
Solution for AngularJS bellow:


 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
private static final int ANGULARJS_TIMEOUT = 30;
private static final int WAIT_FOR_NEXT_CHECK = 1;
public static final Function<JavascriptExecutor, Boolean> angularJSInProgress = (JavascriptExecutor drv) -> {
    String ngFinishedAllRequests = "var pendingRequests = angular.element(document.body).injector().get('$http').pendingRequests;"
            + " return (pendingRequests.length === 0)";
    return (boolean) drv.executeScript(ngFinishedAllRequests);
};

public static void waitForAngularJS(WebDriver webDriver, int secondTimeout) {
    Stopwatch stopwatch = Stopwatch.createStarted();
    boolean inProgress = angularJSInProgress.apply((JavascriptExecutor) webDriver);
    while (!inProgress) {
        inProgress = angularJSInProgress.apply((JavascriptExecutor) webDriver);
        if(stopwatch.elapsed(TimeUnit.SECONDS) > secondTimeout){
            throw new TimeoutException("Timeout occured - " + stopwatch.elapsed(TimeUnit.SECONDS));
        }
        try {
            TimeUnit.SECONDS.sleep(WAIT_FOR_NEXT_CHECK);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

You can use the method waitForAngularJS to wait for a response from server and do not try to guess how long it can take.
In the same way I resolved synchronization with VueJS.
I didn't try to resolve connection state in case of jquery or native request in a different way than add counter of begun connections. Maybe such information is available somewhere in browser driver.

Sunday, 26 March 2017

This week 6/2017

I did fast research of Vue.js (v. 2.2.2) and I'd like to summary what I got to know about it and how it presents itself in compared to Angular 2 and what I think about it.

1. Performance
Project krausest/js-framework-benchmark tested over 20 JavaScript frameworks, below are results.

src: js-frameworks-benchmark4

As you can see in most cases Angular 2 is slower than Vue.js.


2. Size of attached scripts.
In my case small Angular 2 project with 3 additional modules takes 800kb (prod version and after minification). I wonder to know what will be the size with Vue.js. I found comparison of raw frameworks on Vuejs's web side. Vue.js size is about 23kb but Angular 2 about 50kb. It's really interesting....


3. Learning curve
The creators of Vue framework estimate that it is possible to learn their framework in one day or faster if you know AngularJs. I will see ...
In my opinion to learn Angular 2 in one day is impossible. The same is with AngularJs but I think it was easier then with Angular 2.

4. Testing
On project web page unit testing looks similar to Angular Js or Angular 2 unit.



Resources:
  1. https://github.com/krausest/js-framework-benchmark
  2. http://stefankrause.net/js-frameworks-benchmark4/webdriver-ts/table.html
  3. http://www.valuecoders.com/blog/technology-and-apps/vue-js-comparison-angular-react/
  4. https://vuejs.org/v2/guide/comparison.html#Angular-2

Sunday, 5 March 2017

This week 4/2017

This post collects some of my experiences about creating E2E test in protractor using TypeScript for AngularJs page.
At the beginning, it is required to prepare protractor (v4.0.9) configuration. Mine is below.


 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
28
29
exports.config = {
  specs: [
    './e2e/angularjs/**/*.e2e-spec.ts'
  ],
  capabilities: {
    'browserName': 'chrome',
  },
  directConnect: true,
  baseUrl: 'http://localhost:8080/test/',

  framework: 'jasmine',
  rootElement: 'html',
  jasmineNodeOpts: {
        // If true, display spec names.
        isVerbose: true,
        // If true, print colors to the terminal.
        showColors: true,
        // If true, include stack traces in failures.
        includeStackTrace: true,
        // Default time to wait in ms before a test fails.
        defaultTimeoutInterval: 120000
  },
  // compile ts files before run test
  beforeLaunch: function() {
    require('ts-node').register({
      project: 'e2e'
    });
  }
};

In my case I have application which isn't single-page application but every functionality requires to load separate page. However I am going to change it if I find free time.

My notices & tips:
  1. It is good to create a utils class with static methods.
  2. Create one shared authorization method to use it in all tests.
  3. For some test it is good to logout and even clean cookies. It is possible by code: browser.driver.manage().deleteAllCookies();
  4. Sometimes it is good to create screen shot. It is easy to do it.

  5.  1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    browser.takeScreenshot().then((png) => {
      let date = new Date();
      let path = './target/_test-output'
      if(!existsSync(path)){
        mkdirSync(path);
      }
      let stream = createWriteStream(path + '/test_' + date.getTime() + '.png');
      stream.write(new Buffer(png, 'base64'));
      stream.end();
    });
    
  6. In configuration file it is good to set long enough timeout interval. I assumed 2 minutes. It is possible to set other, then default 11 sec, timeout in synchronisation mode - parameter allScriptsTimeout.
  7. Look out if you use $timeout. Some demon task can lock synchronisation and test will fail on timeout. Better use $interval.
  8. If you don't use synchronisation, warm up your application before test or set sleep time before each action loading data from server. Ex. My application load dictionaries from db but all constant values are archived in cache. Loading from db is of course much longer then from cache. It is important to remember about it. 
  9. Some examples of css selectors:  
  • td:nth-child(2) input
  • td:nth-child(1) img#saveButton
  • input[title="Is active?"]




Saturday, 8 October 2016

This week 15/2016

Protractor framework.

The Protractor (v4.0.x) is perfect tool to testing Angular JS application. The main advantage is that it transparently supports asynchronous tasks. You don't care of timeout for Angular asynchronous operation, Protractor is synchronising itself for you. Big advantage is that framework can make snapshot of screen and save it to ex. PNG file.