代码之家  ›  专栏  ›  技术社区  ›  James-Jesse Drinkard

如何为REST API调用编码URL参数?

  •  0
  • James-Jesse Drinkard  · 技术社区  · 7 年前

    我必须创建一些在REST API调用中使用的url参数。我使用Angularjs 1.4.2和一个表单将参数传递给服务函数,服务函数构建参数并生成$http。对API的post调用。我为参数构建块创建了一个plunker。

    索引.html

    <!DOCTYPE html>
    <html>
    
      <head>
        <script data-require="angular.js@1.4.2" data-semver="1.4.2" src="https://code.angularjs.org/1.4.2/angular.js"></script>
        <link rel="stylesheet" href="style.css" />
        <script src="script.js"></script>
      </head>
    
      <body ng-app="app">
        <div ng-controller="mainCtrl">
          testData is: {{testData}}<p></p>
          The data is: {{data}}
        </div>
      </body>
    
    </html>
    

    // Code goes here
    var app = angular.module("app", []);
    
    app.controller('mainCtrl', function($scope, $httpParamSerializerJQLike) {
        //Create JavaScript object.
       var testData = {};
    
        //Load the object with the same data as data.
        testData = loadTestData(testData);
        console.log("testData is: " + JSON.stringify(testData));
        //testData is: {"username":"james@gmail.com","password":"myPassword","grant_type":"password","env":"dev"}
    
        //Use stringify to make it into a JSON string.
        $scope.testData = $httpParamSerializerJQLike(JSON.stringify(testData));
        //Decoded testData
        //={"username":"james@gmail.com","password":"myPassword","grant_type":"password","env":"dev"}
    
        $scope.data = $httpParamSerializerJQLike({
          "username":"james@gmail.com",
          "password":"myPassword",
          "grant_type":"password",
          "env": "dev"
        });
    
    
        function loadTestData(testData){
          testData.username = "james@gmail.com";
          testData.password = "myPassword";
          testData.grant_type = "password";
          testData.env = "dev";
          return testData; 
        }
    });
    

    我将硬编码数据放入一个名为data的变量中,然后使用$httpParamSerializerJQLike来序列化数据。使用我的硬编码数据,即所谓的数据,一切都很好,我在实际代码中从API调用获得HTTP 200成功响应。

    因此,我为参数创建了一个名为testData的JavaScript对象,并使用JSON将其从对象转换为JSON。stringify,然后使用httpParamSerializerJQLike序列化数据。然而,硬编码的(数据)看起来不像testData,它抛出了HTTP 401错误。

    我创建了一个 plunker 试着看看发生了什么。在plunker中,硬编码(数据)的结果如下:

    数据为: env=开发(&D);grant_type=密码(&U);密码=我的密码(&P);用户名=james@gmail.com

    以下是testData的最终结果:testData是:

    解码的测试数据显然不适合URL字符串;

    =“username”:james@gmail.com“,“password”:“myPassword”,“grant\u type”:“password”,“env”:“dev”}

    为什么会这样?我必须手动创建一个函数来创建URL字符串,还是有其他解决方案?

    3 回复  |  直到 7 年前
        1
  •  2
  •   georgeawg    7 年前

    我们必须将JavaScript对象赋给函数“httpParamSerializerJQLike()”,而不是像处理JSON.Stringify(testData)那样的字符串。

        $scope.testData = $httpParamSerializerJQLike(testData);
    

    现在输出为:

    testData is: env=dev&grant_type=password&password=myPassword&username=james@gmail.com
    The data is: env=dev&grant_type=password&password=myPassword&username=james@gmail.com
    
        2
  •  0
  •   guest271314    7 年前

    Object.entries() 获取包含JavaScript对象属性和值的数组数组,用 Array.prototype.map() 链条 .join() "" 创建查询字符串

    let o = {
      "username": "james@gmail.com",
      "password": "myPassword",
      "grant_type": "password",
      "env": "dev"
    };
    
    let props = Object.entries(o);
    let params = `?${props.map(([key, prop], index) => 
                    `${key}=${prop}${index < props.length -1 ? "&" : ""}`
                 ).join("")}`;
    
    console.log(params);
        3
  •  0
  •   georgeawg    7 年前

    $http.post

    不需要使用手动编码url参数 $http service 。只需使用 params

    var params = {name: "joe"};
    var config = { params: params };
    
    var httpPromise = $http.post(url, data, config);
    

    请参阅使用此代码完成的编码 DEMO on PLNKR