Test with mouseover & mouseleave only works with 1000ms timeout

1.2k views Asked by At

I have written tests for this directive that shows bootstrap tooltips:

.directive('mwTooltip', function () {
  return {
    restrict: 'A',
    scope: {
      text: '@mwTooltip',
      placement: '@'
    },
    link: function (scope, el) {
      scope.$watch('text', function () {
        el.data('bs.popover').setContent();
      });

      el.popover({
        trigger: 'hover',
        placement: scope.placement || 'bottom',
        content: function(){
          return scope.text;
        },
        container: 'body'
      });

      var destroyPopOver = function(){
        var popover = el.data('bs.popover');
        if (popover && popover.tip()) {
          popover.tip().detach().remove();
        }
      };

      scope.$on('$destroy', function () {
        destroyPopOver();
      });
    }
  };
})

This test does not pass:

describe('mwTooltip', function () {
  var $compile;
  var $rootScope;
  var scope;
  var el;
  var isolateScope;

  beforeEach(module('mwComponents'));

  beforeEach(inject(function (_$compile_, _$rootScope_) {
    $compile = _$compile_;
    $rootScope = _$rootScope_;
    scope = _$rootScope_.$new();

    el = angular.element(
      '<span mw-tooltip="Tooltip"></span>'
    );

    $compile(el)(scope);
    isolateScope = el.isolateScope();
    scope.$digest();
  }));

  afterEach(function () {
    scope.$destroy();

  });

  it('should show and remove a tooltip', function () {
    el.trigger('mouseover');
    expect(angular.element('.popover').text()).toEqual('Tooltip');

    el.trigger('mouseleave');
    expect(angular.element('.popover').text()).toEqual('');
  });

});

The error is:

PhantomJS 1.9.8 (Mac OS X 0.0.0): Executed 114 of 311 SUCCESS (0 secs / 0.446 secs)
PhantomJS 1.9.8 (Mac OS X 0.0.0) mwTooltip should show and remove a tooltip FAILED
Expected 'Tooltip' to equal ''.
  at /Users/mles/portal-admin/test/ui/mwComponents/mw-tooltip.js:34
PhantomJS 1.9.8 (Mac OS X 0.0.0): Executed 306 of 311 (1 FAILED) (skipped 5) (18.48 secs / 18.539 secs)

However if I run the test as a single test it works(notice the fbefore the it)

fit('should show and remove a tooltip', function () {
  el.trigger('mouseover');
  expect(angular.element('.popover').text()).toEqual('Tooltip');

  el.trigger('mouseleave');
  expect(angular.element('.popover').text()).toEqual('');
});

Also works with a timeout

it('should show and remove a tooltip', function (done) {
  el.trigger('mouseover');
  expect(angular.element('.popover').text()).toEqual('Tooltip');

  el.trigger('mouseleave');
  setTimeout(function(){
    expect(angular.element('.popover').text()).toEqual('');
    done();
  }, 1000);
});

What could be the reason that this test only works as a single test or with a timeout and not when run with the other 300? Looks like PhantomJS is too slow to process the mouseleave in time if other tests have run before.

0

There are 0 answers