From c7a6197bed59969660b6c4e50dd04cd437144bba Mon Sep 17 00:00:00 2001 From: Ofir Dagan Date: Tue, 2 Sep 2014 15:22:17 +0300 Subject: [PATCH] fix(widgets): remove call to $apply in case the caller injector is himself --- angular-widget.js | 23 +++++++++++++---------- app/scripts/services/widgets.js | 24 ++++++++++++++---------- test/spec/services/widgets.spec.js | 21 ++++++++++++++++++--- 3 files changed, 45 insertions(+), 23 deletions(-) diff --git a/angular-widget.js b/angular-widget.js index a125518d..c380ffdb 100644 --- a/angular-widget.js +++ b/angular-widget.js @@ -224,6 +224,18 @@ angular.module("angularWidget").provider("widgets", function() { }; this.$get = [ "$injector", function($injector) { var widgets = []; + function notifyInjector(injector, args) { + var scope = injector.get("$rootScope"); + var isMe = $injector === injector; + var event; + if (args.length) { + event = scope.$broadcast.apply(scope, args); + } + if (!isMe) { + scope.$digest(); + } + return event; + } return { getWidgetManifest: manifestGenerator ? $injector.invoke(manifestGenerator) : angular.noop, unregisterWidget: function(injector) { @@ -247,16 +259,7 @@ angular.module("angularWidget").provider("widgets", function() { notifyWidgets: function() { var args = arguments; return widgets.map(function(injector) { - var scope = injector.get("$rootScope"); - if (args.length) { - var event; - scope.$apply(function() { - event = scope.$broadcast.apply(scope, args); - }); - return event; - } else { - return scope.$digest(); - } + return notifyInjector(injector, args); }); } }; diff --git a/app/scripts/services/widgets.js b/app/scripts/services/widgets.js index f246c447..3fa6c7e9 100644 --- a/app/scripts/services/widgets.js +++ b/app/scripts/services/widgets.js @@ -11,6 +11,19 @@ angular.module('angularWidget') this.$get = function ($injector) { var widgets = []; + function notifyInjector(injector, args) { + var scope = injector.get('$rootScope'); + var isMe = $injector === injector; + var event; + if (args.length) { + event = scope.$broadcast.apply(scope, args); + } + if (!isMe) { + scope.$digest(); + } + return event; + } + return { getWidgetManifest: manifestGenerator ? $injector.invoke(manifestGenerator) : angular.noop, unregisterWidget: function (injector) { @@ -34,16 +47,7 @@ angular.module('angularWidget') notifyWidgets: function () { var args = arguments; return widgets.map(function (injector) { - var scope = injector.get('$rootScope'); - if (args.length) { - var event; - scope.$apply(function () { - event = scope.$broadcast.apply(scope, args); - }); - return event; - } else { - return scope.$digest(); - } + return notifyInjector(injector, args); }); } }; diff --git a/test/spec/services/widgets.spec.js b/test/spec/services/widgets.spec.js index 0aa7054f..b2f6a6a9 100644 --- a/test/spec/services/widgets.spec.js +++ b/test/spec/services/widgets.spec.js @@ -28,14 +28,29 @@ describe('Unit testing widgets service', function () { })); it('should broadcast event when notifyWidgets is invoked with args', inject(function (widgets) { - var applySpy = jasmine.createSpy('$apply').andCallFake(function (fn) { fn(); }); + var digestSpy = jasmine.createSpy('$digest'); var broadcastSpy = jasmine.createSpy('$broadcastSpy').andReturn('shahata'); widgets.registerWidget({get: function (name) { expect(name).toBe('$rootScope'); - return {$apply: applySpy, $broadcast: broadcastSpy}; + return {$digest: digestSpy, $broadcast: broadcastSpy}; }}); expect(widgets.notifyWidgets(1, 2, 3)).toEqual(['shahata']); - expect(applySpy).toHaveBeenCalled(); + expect(digestSpy).toHaveBeenCalled(); + expect(broadcastSpy).toHaveBeenCalledWith(1, 2, 3); + })); + + it('should not call digest in case the caller injector is himself', inject(function (widgets, $injector) { + var digestSpy = jasmine.createSpy('$digest'); + widgets.registerWidget($injector); + widgets.notifyWidgets(); + expect(digestSpy).not.toHaveBeenCalled(); + })); + + it('should call broadcast in case the caller injector is himself', inject(function (widgets, $injector) { + var scope = $injector.get('$rootScope'); + var broadcastSpy = spyOn(scope, '$broadcast'); + widgets.registerWidget($injector); + widgets.notifyWidgets(1, 2, 3); expect(broadcastSpy).toHaveBeenCalledWith(1, 2, 3); }));