4

I have two separate GUIs that are part of the same system. One at the top of the screen (navEditor) and one on the side (routeEditor).

They need two update each other frequently, and call each others functions.

Each has service that holds most of that systems functions. I ran into an issue when I tried to call functions from both A->B and B->A. It, of course, created a circular dependency because I had to include them in each other to gain access.

I looked into several solutions including using $rootScope.$broadcast. However, one common suggestion (found here: angular JS - communicate between non-dependend services) suggested a "subscriber/publisher" method that wired the two together.

This avoids the circular dependency by using a 3rd service and having the other services attach events and handlers to it.

I took this a step further and simply had this parent service return an object with a place holder object for each of my two systems:

//BRIDGE SERVICE
myApp.service('$trafficSys', function(){
     this.sys = {
         navEditor: {}, //poulated by $routeEditor service
         routeEditor: {} ////poulated by $navEditor service
    }
});

//ROUTE-EDITOR
myApp.service('$routeEditor', ['$trafficSys',function($trafficSys) {
    var routeSystem = {
           //entire route editor system goes in here
        }
    $trafficSys.sys.routeEditor = routeSystem;
}]);

//NAV-EDITOR (Same Process as Route Editor)

I then simply had my "navEditor" & " routeEditor" services include $trafficSys and then apply all of thier funcitons to either the navEditor or routeEditor objects.

What I would like to know is if this is considered an Anti-Pattern, and if I am being more imperative rather than declarative.

I am not very experienced with large applications. I'm learning angular so I can push myself to think more about architecture. However, I am finding my lack of foresight is leading me to doubt if i'm doing things the best way.

Any advice would be appreciated.

Community
  • 1
  • 1
Greg G
  • 697
  • 2
  • 8
  • 17
  • Any reason the functions themselves cannot be extracted to the trafficSys service? You've avoided the injection issue, but your architecture is still fundamentally coupled. – Thorn G Dec 15 '14 at 02:26
  • Following up on Tom G's comment, why do the services have to be separate, given how tightly their functionality is coupled? – Hylianpuffball Jan 05 '15 at 03:19

1 Answers1

1

You should leave the business logic to the controller of your angular application.

Have NAV-EDITOR and ROUTE-EDITOR be in separate controllers and have their business logic (function calling) live within a slim controller. While $trafficSys.sys should just be a Singleton that is passed into your controller Dependency inject $routeEditor, $trafficSys and $navEditor into your controller like so:

 myApp.controller('RouteController', ['$scope', '$routeEditor', '$trafficSys' function($scope, $routeEditor) {
      // var trafficSys = $trafficSys.sys 
      //you could even put it on $scope if you need to databind -  $scope.trafficSys = $trafficSys.sys
      //$routeEditor business logic goes here using 
    }]);

myApp.controller('NavController', ['$scope', '$navEditor', '$trafficSys' function($scope, $navEditor) {
      // var trafficSys = $trafficSys.sys 
      //you could even put it on $scope if you need to databind -  $scope.trafficSys = $trafficSys.sys
      //$navEditor business logic goes here
    }]);
Alex Daro
  • 439
  • 1
  • 7
  • 17