SharePoint REST API 和 AngularJs (适用于 2013, 2016 和 Online)






3.86/5 (5投票s)
SharePoint 和 AngularJs 以及 HTTP 请求,例如 GET, POST, UPDATE, DELETE 和使用 AngularJS 进行文件上传
引言
此示例包含一个可重用的 angularjs 模块。该模块包含一个服务和一个指令。任何人都可以通过依赖注入使用此模块。这适用于希望利用 SharePoint 客户端开发中双向数据绑定的用户。在客户端开发中,我们基本上会向一些特定的端点发出 GET
, POST
, UPDATE
和 DELETE
请求。因此,此模块将为您节省编写任何 HTTP
请求的代码冗余。该模块适用于内容编辑器 Web 部件和 SharePoint 托管应用开发。
开始之前
目标用户在使用此模块之前需要具备以下知识。我将在下面提供一些相关内容的参考。
当前问题
获取所有列表的典型 GET
请求如下所示:
function getAllLists() {
$http({
url: "/_api/web/lists"
method: "GET",
headers: {
"accept": "application/json;odata=verbose",
"content-Type": "application/json;odata=verbose"
}
}).success(function(result) {
//do something here
}).error(function(error, status) {
// do something here
});
}
而获取特定列表所有项目的 GET
请求如下所示:
function getAllItems() {
$http({
url: "/_api/web/lists/GetByTitle('List Title')/Items"
method: "GET",
headers: {
"accept": "application/json;odata=verbose",
"content-Type": "application/json;odata=verbose"
}
}).success(function(result) {
//do something here
}).error(function(error, status) {
// do something here
});
}
这些函数的作用不同,但它们共享大部分代码。因此,该模块负责处理 GET
, POST
, UPDATE
和 DELETE
请求的所有繁琐工作。您只需传递您的 data
和 url
即可发出任何类型的请求。此模块的源代码如下所示:
(function() {
'use strict';
angular.module('spNgModule', []).factory
("spBaseService", spBaseService).directive("customFileChange", customFileChange);;
spBaseService.$inject = ["$q", "$http", "IS_APP_WEB"];
function spBaseService($q, $http, isAppWeb) {
var baseUrl = isAppWeb ? _spPageContextInfo.webAbsoluteUrl :
_spPageContextInfo.siteAbsoluteUrl;
return {
getRequest: getRequest,
postRequest: postRequest,
updateRequest: updateRequest,
deleteRequest: deleteRequest,
fileUploadRequest: fileUploadRequest,
baseUrl: baseUrl
};
function getRequest(query, endPoint) {
var deferred = $q.defer();
$http({
url: endPoint || baseUrl + query,
method: "GET",
headers: {
"accept": "application/json;odata=verbose",
"content-Type": "application/json;odata=verbose"
}
}).success(function(result) {
deferred.resolve(result);
}).error(function(result, status) {
deferred.reject({
error: result,
status: status
});
});
return deferred.promise;
}
function postRequest(data, url, endPoint) {
var deferred = $q.defer();
$http({
url: endPoint || baseUrl + url,
method: "POST",
headers: {
"accept": "application/json;odata=verbose",
"X-RequestDigest": document.getElementById("__REQUESTDIGEST").value,
"content-Type": "application/json;odata=verbose"
},
data: JSON.stringify(data)
}).success(function(result) {
deferred.resolve(result);
}).error(function(result, status) {
deferred.reject({
error: result,
status: status
});
});
return deferred.promise;
}
function fileUploadRequest(data, url, endPoint) {
var deferred = $q.defer();
$http({
url: endPoint || baseUrl + url,
method: "POST",
processData: false,
data: data,
transformRequest: angular.identity,
headers: {
"accept": "application/json;odata=verbose",
"X-RequestDigest": document.getElementById("__REQUESTDIGEST").value,
"Content-Type": undefined
}
}).success(function(result) {
deferred.resolve(result);
}).error(function(result, status) {
deferred.reject({
error: result,
status: status
});
});
return deferred.promise;
}
function updateRequest(data, url, endPoint) {
var deferred = $q.defer();
$http({
url: endPoint || baseUrl + url,
method: "PATCH",
headers: {
"accept": "application/json;odata=verbose",
"X-RequestDigest": document.getElementById("__REQUESTDIGEST").value,
"content-Type": "application/json;odata=verbose",
"X-Http-Method": "PATCH",
"If-Match": "*"
},
data: JSON.stringify(data)
}).success(function(result) {
deferred.resolve(result);
}).error(function(result, status) {
deferred.reject({
error: result,
status: status
});
});
return deferred.promise;
}
function deleteRequest(url, endPoint) {
var deferred = $q.defer();
$http({
url: endPoint || baseUrl + url,
method: "DELETE",
headers: {
"accept": "application/json;odata=verbose",
"X-RequestDigest": document.getElementById("__REQUESTDIGEST").value,
"IF-MATCH": "*"
}
}).success(function(result) {
deferred.resolve(result);
}).error(function(result, status) {
deferred.reject({
error: result,
status: status
});
});
return deferred.promise;
}
}
customFileChange.$inject = ["$parse"];
function customFileChange($parse) {
return {
restrict: "A",
link: function(scope, element, attrs) {
var model = $parse(attrs.customFileChange);
var modelSetter = model.assign;
element.bind("change", function() {
scope.$apply(function() {
var reader = new FileReader();
reader.onload = function(e) {
var fileModel = {
fileName: element[0].files[0].name,
fileAsBuffer: e.target.result
};
modelSetter(scope, fileModel);
}
reader.onerror = function(e) {
alert(e.target.error);
}
reader.readAsArrayBuffer(element[0].files[0]);
});
});
}
};
}
})(window, document);
此模块包含的内容
getRequest(query, endPoint)
postRequest(data, url, endPoint)
updateRequest(data, url, endPoint)
deleteRequest(url, endPoint)
fileUploadRequest(data, url, endPoint)
endPoint
在所有地方都是可选的。稍后将讨论其用法。您将能够使用支持 GET
, POST
, UPDATE
和 DELETE
请求的这些端点。每个方法都会返回一个 Promise,您需要在代码中对其进行处理。
如何使用
首先,从附件下载此模块。附件包含我的模块的最小化和非最小化版本。下载文件后,请在您的项目中添加引用。例如,在 SharePoint 托管应用中,应如下所示:
<script src="../Scripts/App/spNgModule.js"></script>
在内容编辑器 Web 部件中,您需要将此文件上传到某个库,然后才能使用它。
在模块中添加依赖
您可以通过以下方式将此依赖项添加到您的模块中。此模块的名称是 spNgModule
。
(function () {
angular.module("spNgModuleTest", ["spNgModule"])
.constant("IS_APP_WEB", false);
})();
在这里,您需要指定 IS_APP_WEB
的值。这意味着将使用哪个 Web URL 来发出 GET
, POST
, UPDATE
和 DELETE
请求。在指定 IS_APP_WEB
的值之后,您还可以使用其他 URL 来发出任何请求。这就是为什么有一个名为 endPoint
的可选参数。
注意:如果您在请求中指定了 endPoint
,那么 url
参数将是可选的。默认情况下,所有请求都将基于 IS_APP_WEB
的值发出。无论是 APP Web 还是 Host Web。
注入服务
我使用的服务名称是 spBaseService
。因此,您可以按以下方式注入此服务:
angular.module("spNgModuleTest")
.factory("spNgTestSvc", spNgTestSvc);
spNgTestSvc.$inject = ["spBaseService"];
GET 请求示例
spBaseService.getRequest(query, endPoint)
您可以传递支持 HTTP GET
请求的任何查询或端点。例如:
您想获取当前站点下的所有列表
function getAllLists() {
var query = "/_api/web/lists?$select=Title";
return spBaseService.getRequest(query);
}
如果您想获取列表的所有项目,那么将是:
function getAllItems() {
var query = "/_api/web/lists/GetByTitle('List Title')/Items";
return spBaseService.getRequest(query);
}
如果您想获取所有子站点,那么将是:
function getSubSites() {
var query = "/_api/Web/Webs";
return spBaseService.getRequest(query);
}
所以,我通过这些示例想说的是:只需发出任何 GET
请求,您就需要处理查询或端点。
endPoint 参数的使用
有些人可能需要在以下场景中使用 endPoint
:
假设您当前的站点是 https://xxx.sharepoint.com
(可以是 Host Web 或 App Web)。现在您想对子站点 https://xxx.sharepoint.com/hr
发出 GET
, POST
, UPDATE
或 DELETE
请求,或者从 App Web 对 Host Web 发出 GET
, POST
, UPDATE
或 DELETE
请求。在这种情况下,您需要使用 endPoint
。
function getSubSites() {
var endPoint = "https://xxx.sharepoint.com/hr/_api/Web/Webs";
return spBaseService.getRequest(null, endPoint);
}
POST 请求示例
这适用于添加新对象(列表项、文件、站点、文档等)。
spBaseService.postRequest(data, url, endPoint)
data
是请求体。它会因请求而异。例如,要添加一个子站点,请求体应如下所示:
var data = {
parameters: {
__metadata: {
'type': 'SP.WebInfoCreationInformation'
},
Url: "site url",
Title: "site title",
Description: "site description",
Language: 1033,
UseUniquePermissions: true
}
};
url
是任何支持 POST
请求的端点。要添加子站点,端点是:
var url = "/_api/web/webinfos/add";
endPoint
的用法可以在 此处 找到。
因此,添加站点的完整 POST
请求是:
function addSubSite() {
var data = {
parameters: {
__metadata: {
'type': 'SP.WebInfoCreationInformation'
},
Url: "site url",
Title: "site title",
Description: "site description",
Language: 1033,
UseUniquePermissions: true
}
};
var url = "/_api/web/webinfos/add";
return spBaseService.postRequest(data, url);
}
UPDATE 请求示例
spBaseService.updateRequest(data, url, endPoint);
它与 POST
请求几乎相同。您可以使用此方法更新站点中的任何对象。看看更新特定列表中的项目。
function updateItemById(itemId) { var url = "/_api/web/lists/GetByTitle('List Name')/GetItemById(" + itemId + ")"; var data = { __metadata: { type: "SP.Data.SpNgListListItem" }, Title: "New sp ng item updated " + Math.random() }; return spBaseService.updateRequest(data, url); }
请在此处 查看 endPoint
的用法。
DELETE 请求示例
spBaseService.deleteRequest(url, endPoint);
您将使用此方法从站点中删除某些内容。假设我们要删除 ID
等于 5
的项目。
function deleteAnItem() { var url = "/_api/web/lists/GetByTitle('List Name')/GetItemById(5)"; return spBaseService.deleteRequest(url); }
请在此处 查看 endPoint
的用法。
文件上传示例
spBaseService.fileUploadRequest(data, url, endPoint);
在请求体中,您需要将文件作为 ArrayBuffer
传递。如前所述,此模块还包含一个指令,该指令将帮助您以 ArrayBuffer
格式获取文件。该指令的名称是 customFileChange
。用于上传的 HTML 应如下所示:
<input type="file" data-custom-file-change="attachment" />
attachment
是模型,它将为您提供 ArrayBuffer
格式的文件。您可以根据需要更改其名称。您将从此模型中获得两个属性,例如 fileName
和 fileAsBuffer
。
以下是上传 ID 等于 2
的特定项目的附件的示例:
function uploadAttachment(attachment){
var url = "/_api/web/lists/GetByTitle('SpNgList')/items(2)/
AttachmentFiles/add(FileName='" + attachment.fileName + "')";
return spBaseService.fileUploadRequest(attachment.fileAsBuffer, url);
}
请在此处 查看 endPoint
的用法。
处理响应示例
您将从上述所有方法中获得一个 Promise 作为返回值。因此,这与典型的响应处理 Angular 代码相同。例如:
spNgTestSvc.addSubSite() .then(function(successResponse) { // code after success }, function(errorrResponse) { //code after error });
errorResponse
有两个属性,例如 error
和 status
。error
是 SharePoint 端点返回的实际错误对象。
结论
以上就是我当前模块的全部内容。我将尝试在未来的更新中使其变得更好。由于我的源代码是开放的,如果您能收到读者的任何反馈和建议,我将非常高兴。
历史
- 2016 年 7 月 29 日:初始版本