0

I am trying to modify my controller's variables from within a call to $http (which receives data from an API). These controller variables are bound in my view with ng-model.

However, it's not working -- nothing is displaying!

angular
    .module('myApp')
    .controller('contactController', ['$scope', '$http', ContactController]);

function ContactController($scope, $http) {

    this.firstName = '';
    this.lastName = '';

    $http.get('../server/getdata').success(function(data) {
        // I would like to set the firstName and lastName variables 
        // from the above parent scope into here. Is this possible? 
        this.firstName = data.firstName;
        this.lastName = data.lastName;
    });
}

Any thoughts here??

3 Answers 3

1

Just need to preserve the value of this at the time the capture is created by assigning it to another variable such as self

angular
    .module('myApp')
    .controller('contactController', ['$scope', '$http', ContactController]);

function ContactController($scope, $http) {

    var self = this;

    this.firstName = '';
    this.lastName = '';

    $http.get('../server/getdata').success(function(data) {
        // I would like to set the firstName and lastName variables 
        // from the above parent scope into here. Is this possible? 
        self.firstName = data.firstName;
        self.lastName = data.lastName;
    });
}
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks @JC! This is similar to Phil's response as well. However, are you able to comment why (if) these approaches are preferred to using $scope? I've seen $scope used in online examples, while I was researching for ways to get this to work
Using $scope is just another way of saving a reference to the controller. The real problem is the variable this. It refers to the controller when the controller is being instantiated, but it changes to a different object when the $http callback is executed so you need another way of referring to the controller within that callback. If the controller is attached to $scope for instance as member named ctrl you can just reference it there like so: $scope.ctrl.firstName. However, in my opinion that's less clear than explicitly saving the reference in the closure.
1

The problem is this in the $http callback is no longer your controller.

Assign the this value to a scoped variable, eg

var ctrl = this;

ctrl.firstName = '';
ctrl.lastName = '';

// keep in mind the "success" and "error" methods on the $http promise
// have been deprecated. Use the standard "then" method instead.
$http.get('../server/getdata').then(function(response) {
    ctrl.firstName = response.data.firstName;
    ctrl.lastName = response.data.lastName;
});

See https://docs.angularjs.org/api/ng/service/$http#deprecation-notice regarding the deprecated $http callback methods.

2 Comments

Thanks @Phil. This worked; also thanks for the heads up to start using "then" instead of "success"!
@Ricky some reading is available here ~ toddmotto.com/digging-into-angulars-controller-as-syntax
-1

Change this to $scope in success function so your code will be like

$scope.firstName = data.firstName;
$scope.lastName = data.lastName;

this inside success function has function scope not global scope so this does not bind to controller.

2 Comments

Presumably OP is using a "controller-as" expression and as such, suggesting they use $scope is not applicable.
@Phil: I've seen some examples online of using this "$scope" object in the manner described by Sarjan, here. What is the difference between using this $scope and using var self = this, for example? (and then referencing "self" in the inner function)

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.