0

I am having trouble when using multiple instances of the following directive. Randomly, I will get the wrong list back in my success method. scope.type is always 'correct'; meaning it is what I passed in. The response will sometimes be the response from a different call.

The directive:

angular.module('dincApp.directives').directive('lwSelect',
   ['$log', 'optionsService', '$http',
   function ($log, optionsService, $http) {

   return {
      restrict: 'E',
      replace: true,

      scope:{
         placeholder : '@',
         type : '@'
      },

      link: function (scope, element, attr) {
         $log.info('scope.type = ' + scope.type);

         scope.options = {};

         $http({method: 'GET', url: '/options/' + scope.type}).
            success(function(data, status, headers, config) {
               $log.info('scope.type = ' + scope.type);
               $log.info('data = ' + JSON.stringify(data));
               scope.options = data;
            }).
            error(function(data, status, headers, config) {
               $log.debug('Error retrieving select options');
            });
      },

      template:
         '<select ng-options="option.key as option.value for option in options" ' +
         '>' +
         '<option value="">-- {{placeholder}} {{type}} --</option>' +
         '</select>'

   };
}]);

The html:

<lw-select id="stateSelect"
           placeholder="State"
           class="form-control"
           name="state"
           ng-model="profile.state"
           type="State"
           >
</lw-select>

Any ideas? I tried using a $resource as well, but the same issue occurs. I'm not sure it's related to the directive. I experienced similar behavior when I made several calls to the same $resource in a controller too.

UPDATE:

I have moved this logic out of the directive into the controller and experience the same issue. These calls in the controller will work some of the time. Others I will get the list of states returned for the countries and vice versa. It's like there is a race condition. Are these calls not separate instances?

Controller:

       optionsService.retrieve({optionType:"State"}).$promise.then(
           function success(response) {
              $log.debug('Options response for stateOptions:' + JSON.stringify(response));
              $scope.stateOptions = response;
           },
           function failure() {
              $log.error('Error retrieving select options');
           });

        optionsService.retrieve({optionType:"Country"}).$promise.then(
           function success(response) {
              $log.debug('Options response for countryOptions:' + JSON.stringify(response));
              $scope.countryOptions = response;
           },
           function failure() {
              $log.error('Error retrieving select options');
           });
        ....

Resource:

angular.module('dincApp.services').factory('optionsService',
['$resource',
  function ($resource) {
     return $resource('/options/:optionType', {}, {
        retrieve: { method: 'GET', isArray: true }
     });
  }]);
3
  • It's a bit hard to tell exactly what you mean but try setting a variable to your $http return (ie the promise) and in the 'then' set the data. var val = $http(....); val.then(function(data) { $scope.options = data;}); That sort of thing Commented Sep 24, 2014 at 0:08
  • Basically, I have several instances of the directive on the same page. I thought I was using isolation scope. scope.type looks correct in my logs. They randomly have each others return data. Commented Sep 24, 2014 at 1:19
  • rather than doing this in link do it in controller Commented Sep 24, 2014 at 2:09

1 Answer 1

1

Rather than doing this in link do it in controller:

angular.module('dincApp.directives')

.directive('lwSelect', ['$log', 'optionsService', '$http',
    function ($log, optionsService, $http) {

        return {
            restrict: 'E',
            replace: true,

            scope: {
                placeholder: '@',
                type: '@'
            },

            controller: ['$scope', function (scope) {
                $log.info('scope.type = ' + scope.type);

                scope.options = {};

                $http({
                    method: 'GET',
                    url: '/options/' + scope.type
                }).
                success(function (data, status, headers, config) {
                    $log.info('scope.type = ' + scope.type);
                    $log.info('data = ' + JSON.stringify(data));
                    scope.options = data;
                }).
                error(function (data, status, headers, config) {
                    $log.debug('Error retrieving select options');
                });
           }],

            template: '<select ng-options="option.key as option.value for option in options" ' +
                '>' +
                '<option value="">-- {{placeholder}} {{type}} --</option>' +
                '</select>'
        };
    }]);
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.