Contents

AngularJS 的 REST API简介

1. 概述

在这个快速教程中,我们将学习如何从一个简单的 AngularJS 前端使用 RESTful API。

我们将在表格中显示数据,创建资源,更新它,最后删除它。

2. REST API

首先,让我们快速浏览一下我们的简单 API——使用分页公开Feed资源:

  • 分页 - GET /api/myFeeds?page={page}&size={size}&sortDir={dir}&sort={propertyName}
  • 创建 - POST /api/myFeeds
  • 更新 – PUT /api/myFeeds/{id}
  • 删除 - DELETE /api/myFeeds/{id}

这里的一个快速说明是分页使用以下 4 个参数:

  • page : 请求页面的索引
  • size : 每页最大记录数
  • sort : 用于排序的属性名称
  • sortDir : 排序方向

以下是Feed资源的示例:

{
    "id":1,
    "name":"blogdemo feed",
    "url":"/feed"
}

3. List页面

现在,让我们看看我们的List页面:

<script 
  src="http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.min.js">
</script>
<script 
  src="http://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular-resource.min.js">
</script>
<script th:src="@{/resources/ng-table.min.js}"></script>
<script th:src="@{/resources/mainCtrl.js}"></script>
<a href="#" ng-click="addNewFeed()">Add New RSS Feed</a>
<table ng-table="tableParams">
    <tr ng-repeat="row in $data track by row.id">
        <td data-title="'Name'" sortable="'name'">{{row.name}}</td>
        <td data-title="'Feed URL'" sortable="'url'">{{row.url}}</td>
        <td data-title="'Actions'">
            <a href="#" ng-click="editFeed(row) ">Edit</a>
            <a href="#" ng-click="confirmDelete(row.id) ">Delete</a>
        </td>
    </tr>
</table>
</div>
</body>
</html>

请注意,我们使用ng-table 来显示数据——更多内容将在以下部分中介绍。

4. AngularJS控制器

接下来,让我们看看我们的 AngularJS 控制器:

var app = angular.module('myApp', ["ngTable", "ngResource"]);
app.controller('mainCtrl', function($scope, NgTableParams, $resource) {
    ...   
});

注意:

  • 我们注入了ngTable模块以使用它在用户友好的表格中显示我们的数据并处理分页/排序操作
  • 我们还注入了 ngResource模块来使用它来访问我们的 REST API 资源

5. AngularJS 数据表

现在让我们快速浏览一下ng-table模块——这是配置:

$scope.feed = $resource("api/myFeeds/:feedId",{feedId:'@id'});
$scope.tableParams = new NgTableParams({}, {
    getData: function(params) {
        var queryParams = {
            page:params.page() - 1, 
            size:params.count()
        };
        var sortingProp = Object.keys(params.sorting());
        if(sortingProp.length == 1){
    	    queryParams["sort"] = sortingProp[0];
    	    queryParams["sortDir"] = params.sorting()[sortingProp[0]];
        }
        return $scope.feed.query(queryParams, function(data, headers) {
            var totalRecords = headers("PAGING_INFO").split(",")[0].split("=")[1];
            params.total(totalRecords);
            return data;
        }).$promise;
    }
});

API 需要某种分页样式,因此我们需要在表格中自定义它以匹配它。我们使用ng-module中的参数并在这里创建我们自己的queryParams

关于分页的一些附加说明:

  • *params.page()*从 1 开始,所以我们还需要确保它在与 API 通信时变为零索引
  • params.sorting()返回一个对象 - 例如{“name”: “asc”},因此我们需要将键和值分隔为两个不同的参数 - sortsortDir
  • 我们从响应的 HTTP 标头中提取总元素数

6. 更多操作

最后,我们可以使用*ngResource 模块执行很多操作—— $resource确实涵盖了可用操作方面的完整 HTTP 语义。我们还可以定义我们的自定义功能。 我们在上一节中使用query来获取提要列表。请注意,getquery都执行GET*——但query用于处理数组响应。

6.1. 添加新Feed

为了添加新的提要,我们将使用*$resource方法save *- 如下:

$scope.feed = {name:"New feed", url: "http://www.example.com/feed"};
$scope.createFeed = function(){
    $scope.feeds.save($scope.feed, function(){
        $scope.tableParams.reload();
    });
}

6.2. 更新Feed

我们可以使用我们自己的自定义方法和*$resource* - 如下:

$scope.feeds = $resource("api/myFeeds/:feedId",{feedId:'@id'},{
    'update': { method:'PUT' }
});
$scope.updateFeed = function(){
    $scope.feeds.update($scope.feed, function(){
        $scope.tableParams.reload();
    });
}

请注意我们如何配置自己的update方法来发送PUT请求。

6.3. 删除Feed

最后,我们可以使用delete方法删除一个提要:

$scope.confirmDelete = function(id){
    $scope.feeds.delete({feedId:id}, function(){
        $scope.tableParams.reload();
    });
}

7. AngularJs 对话框

现在,让我们看看如何使用*ngDialog *模块来显示用于添加/更新我们的提要的简单表单。

这是我们的模板,我们可以在单独的 HTML 页面或同一页面中定义它:

<script type="text/ng-template" id="templateId">
<div class="ngdialog-message">
    <h2>{{feed.name}}</h2>
    <input ng-model="feed.name"/>
    <input ng-model="feed.url"/>
</div>
<div class="ngdialog-buttons mt">
    <button ng-click="save()">Save</button>
</div>
</script>

然后我们将打开我们的对话框来添加/编辑一个提要:

$scope.addNewFeed = function(){
    $scope.feed = {name:"New Feed", url: ""};
    ngDialog.open({ template: 'templateId', scope: $scope});
}
$scope.editFeed = function(row){
    $scope.feed.id = row.id;
    $scope.feed.name = row.name;
    $scope.feed.url = row.url;
    ngDialog.open({ template: 'templateId', scope: $scope});
}
$scope.save = function(){
    ngDialog.close('ngdialog1');
    if(! $scope.feed.id){
        $scope.createFeed();
    } else{
        $scope.updateFeed();
    }
}

注意:

  • *$scope.save()*在用户点击对话框中的保存按钮时被调用
  • $scope.addNewFeed()在用户单击提要页面中的添加新feed按钮时被调用——它初始化一个新feed对象(没有id
  • 当用户想要编辑 Feeds 表中的特定行时调用*$scope.editFeed()*

8. 错误处理

最后,让我们看看如何使用 AngularJS 处理响应错误消息。

为了全局处理服务器错误响应——而不是每个请求——我们将向*$httpProvider *注册一个拦截器:

app.config(['$httpProvider', function ($httpProvider) {
    $httpProvider.interceptors.push(function ($q,$rootScope) {
        return {
            'responseError': function (responseError) {
                $rootScope.message = responseError.data.message;
                return $q.reject(responseError);
            }
        };
    });
}]);

这是我们在 HTML 中的消息表示:

<div ng-show="message" class="alert alert-danger">
    {{message}}
</div>