简体   繁体   中英

How to Initialize third party JavaScript asynchronous library before loading AngularJS

I'm facing problem while initializing a third party JavaScript API (iHUB) inside RUN method of AngularJS. Currently the code is behaving in asynchronous mode. I want IHUB to first initialize and then AngularJS route/controller should get called. (Is it possible to make utilization of the callback method provided by IHUB ?)

var nameApp = angular.module('nameApp', ['ngRoute']);

nameApp.run(['$window', 'myService', function($window, myService) {

   //initialize IHUB
   var actuate= new actuate();
   actuate.initialize('http://localhost:8700/iportal', settings.reqOps, "user", "pwd", callback);

   function callback(){
     alert('started!!');
   }

}]);

nameApp.config(['$routeProvider', function($routeProvider) {
  $routeProvider.
    when('/:tabname', {
      templateUrl: 'pages/analyticsDetail.html',
      controller: 'tabDetailCtrl'
    }).
    when('/:tabname/:reportName', {
      templateUrl: 'pages/analyticsDetail.html',
      controller: 'reportDetailCtrl'
    }).
    otherwise({
      redirectTo: '/Buy Side Dashboard'
    });
}]);

There is only one way to achieve a "real" before AngularJS initialization behavior by using angular.bootstrap(); . This allows you to initialize your AngularJS application manually.

Note: You should not use the ng-app directive when manually bootstrapping your app.

> Fiddle demo

View

<div ng-controller="MyController">
  Hello, {{greetMe}}!
</div>

Application

angular.module('myApp', [])
  .controller('MyController', ['$scope', function ($scope) {
    $scope.greetMe = 'World';
  }]);

var actuateDummy = {
  initialize: function (callback) {
    setTimeout(callback, 2500);
  }
};

actuateDummy.initialize(function () {
  angular.element(function() {
    angular.bootstrap(document, ['myApp']);
  });
})

This is an other approach which uses the resolve state of ui-router . This service only initializes iHUB if it not has been initialized yet:

This service also returns the actuate object. In that way you can use it in your controller or components after init.

> Demo fiddle

View

<nav>
  <a ui-sref="state1">State 1</a>
  <a ui-sref="state2">State 2</a>
</nav>

<div ui-view></div>

AngularJS Application

var myApp = angular.module("myApp", ["ui.router"]);

myApp.config(function($stateProvider, $urlRouterProvider) {
  $stateProvider.state("state1", {
    url: "#",
    template: "<p>State 1</p>",
    controller: "Ctrl1",
    resolve: {
      iHubInit: function(iHubService) {
        return iHubService.init()
      }
    }
  }).state("state2", {
    url: "#",
    template: "<p>State 2</p>",
    controller: "Ctrl2",
    resolve: {
      iHubInit: function(iHubService) {
        return iHubService.init()
      }
    }
  });
});

myApp.controller("Ctrl1", function($scope, iHubService) {
  console.log("Ctrl1 loaded.");
});

myApp.controller("Ctrl2", function($scope, iHubService) {
  console.log("Ctrl2 loaded.");
});

myApp.service('iHubService', ["$q", function($q) {

  this.iHubServiceInitialized = false;
  this.actuate = null;

  this.init = function() {

    if (!this.iHubServiceInitialized) {

      //Init
      var self = this;
      var deferred = $q.defer();
      this.actuate = new actuate();

      //initialize
      this.actuate.initialize('http://localhost:8700/iportal', settings.reqOps, "user", "pwd", function() {
        self.iHubServiceInitialized = true;
        deferred.resolve(self.actuate);
      });

      return deferred.promise;
    } else {
      return this.actuate;
    }
  }
}]);

Try to add a resolve attribute when configuring your route provider like below:

var nameApp = angular.module('nameApp', ['ngRoute']);

nameApp.config(['$routeProvider', function($routeProvider) {
  $routeProvider.
    when('/:tabname', {
      templateUrl: 'pages/analyticsDetail.html',
      controller: 'tabDetailCtrl',
      resolve: {
                ihubInit: ['iHubService', function (iHubService) {
                    return iHubService.init();
                }]
            }
    }).
    when('/:tabname/:reportName', {
      templateUrl: 'pages/analyticsDetail.html',
      controller: 'reportDetailCtrl',
      resolve: {
                ihubInit: ['iHubService', function (iHubService) {
                    return iHubService.init();
                }]
            }
    }).
    otherwise({
      redirectTo: '/Buy Side Dashboard'
    });
}]);

nameApp.service('iHubService', ["$q", function($q){
  this.init = function() {
    var deferred = $q.defer();
    var actuate= new actuate();
    actuate.initialize('http://localhost:8700/iportal', settings.reqOps, "user", "pwd", callback);

    function callback(){
       deferred.resolve();
    }
    return deferred.promise;
  }
}]);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM