Angular REST cannot return simple data

2019-09-10 14:23发布

问题:

I am trying to get a $http REST GET call working in my Appgyver project working but nothing I do seems to come right, always returns an error.

Please note the angular app will be running on mobile devices eventually and then connect to my remote web service.

I've double checked that my custom API is working and returning data correctly in a number of ways, namely:

  • hard coded cUrl request running from sh files in terminal - Returns data and correct 200 code
  • Tested the API end points in both POSTMAN and Firefox's SOA client.

Putting in my test end point of http://somesite.com/quote-and-buy-performance/druidapi/taxonomy_term returns data as below:

[{"tid":"1","vid":"2","name":"ACME Ltd.","description":"","format":"filtered_html","weight":"0","parent":"0","uri":"http://somesite.com/quote-and-buy-performance/druidapi/taxonomy_term/1"},{"tid":"2","vid":"2","name":"ABC Films LTD","description":"","format":"filtered_html","weight":"0","parent":"0","uri":"http://somesite.com/quote-and-buy-performance/druidapi/taxonomy_term/2"}]

Even a simple CSRF Token request gives me errors.

Could someone possibly point out where I am going wrong here, the Appgyver site is badly documented and I have tried the Angular RESTful sample which my code below is based upon from https://docs.angularjs.org/api/ng/service/$http and https://docs.angularjs.org/api/ng/service/$http#setting-http-headers

Please note the code below is basically Angular.js using Javascript syntax (as opposed to Coffeescript), logging output follows the code

angular
.module('main')
.controller('LoginController', function($scope, supersonic, $http) {
    $scope.navbarTitle = "Settings";

    $scope.stoken = "Response goes here";

    $scope.processLogin = function(){
        var csrfToken;

        steroids.logger.log("START CALL: processLogin");

        // $form_login_email_address = $scope.login_email;
        // $form_login_password = $scope.login_password;

        $local_get = "http://somesite.com/quote-and-buy-performance/services/session/token";
        $hal_get_taxterm_index = "http://somesite.com/quote-and-buy-performance/druidapi/taxonomy_term";

        // $http.defaults.headers.common.contentType('application/json');

        var req = {
            method: 'GET',
            url: $hal_get_taxterm_index,
            headers: {
                'Content-Type': 'application/json'
            }
        }

        $http(req)
          .success(function(data, status, headers) {
            steroids.logger.log("Inside http.get() success");
        }).error(function(data, status, headers){
            steroids.logger.log("Inside http.get() WITH ERROR");
            steroids.logger.log('data: ' + data);
            steroids.logger.log('status: ' + status);
        }).then(function(data, status, headers){
            steroids.logger.log("Inside http.get() then");
        });

        steroids.logger.log("END CALL: processLogin");
    }

});

Logging output from calls to steroids.logger.log

View        Time            Level   Message
main#login  16:01:55.219    info    "Inside http.get() WITH ERROR"
main#login  16:01:55.219    info    "data: null"
main#login  16:01:55.219    info    "status: 0"
main#login  16:01:55.64     info    "END CALL: processLogin"
main#login  16:01:55.64     info    "START CALL: processLogin"

回答1:

Here's what I would do:

Separate out your http call into a service. This is a pretty standard way to modularize your code in angular:

angular.module('main').factory("SomeService", function($http) {
  return {
    get: function() {
      $http({
        url: "http://somesite.com/quote-and-buy-performance/druidapi/taxonomy_term",
        method: "GET",
        headers: {
          "Content-Type": "application/json"
        }
      }).success(function(data, status, headers, config) {
        console.log("Success!");
        console.log(data);
      }).error(function(data, status, headers, config) {
        console.log("Error!");
        console.log(status);
        console.log(data);
      });
    }
  }
})

Then to use this in your controller, just include it in your controller declaration and call get like you would a normal method:

angular.module('main').controller('LoginController', function($scope, supersonic, SomeService) {
  $scope.navbarTitle = "Settings";
  $scope.stoken = "Response goes here";
  $scope.processLogin = function(){
    var csrfToken;
    steroids.logger.log("START CALL: processLogin");

    SomeService.get();

    steroids.logger.log("END CALL: processLogin");
  }
})

Do this and then comment back with your results and we can work from there.



回答2:

If your angular's app is within a certain domain, then HTTP request must be made within the same domain.

In your case, you are trying a cross domain request (a request on another domain). You must then make a cross domain request.

You can see this question.

The author uses $http.jsonp() to send cross domain requests. There migth be another way to do it.