SharePoint List items can have one or more attachments. This post describes how to save/upload attachments and how to retrieve/download them for a specific list item in a list using SharePoint client REST API using Javascript.
Uploading an Attachment to SharePoint List using REST API using Javascript
First we have to read the file content and then upload the file to the list item as an attachment. I have used HTML 5 FileReader in order to read the file content. You have to pass the control id of your file input control to the following function. The function returns a promise that we can use to get the output.
1: function readFile (uploadControlId) {
2:
3: if (!window.FileReader)
4: throw "The browser does not support HTML 5";
5:
6: var def = new $.Deferred();
7:
8: var element = document.getElementById(uploadControlId);
9: var file = element.files[0];
10: var parts = element.value.split("\\");
11: var fileName = parts[parts.length - 1];
12:
13: var reader = new FileReader();
14: reader.onload = function (e) {
15: def.resolve(e.target.result, fileName);
16: }
17: reader.onerror = function (e) {
18: def.reject(e.target.error);
19: }
20:
21: reader.readAsArrayBuffer(file);
22:
23: return def.promise();
24: }
The following function upload the attachment to the specified list. It takes the ID of the list item as the first parameter, list name as the second parameter, file name and buffer go as third and fourth parameters which we get from the above function.
1: function uploadAttachment (id, listName, fileName, buffer) {
2: var url = _spPageContextInfo.webServerRelativeUrl +
3: "/_api/web/lists/getByTitle('" + listName + "')/items('" + id.toString() + "')/AttachmentFiles/add(FileName='" + fileName + "')";
4:
5: return $.ajax({
6: url: url,
7: type: "POST",
8: data: buffer,
9: processData: false,
10: headers: {
11: Accept: "application/json;odata=verbose",
12: "X-RequestDigest": $("#__REQUESTDIGEST").val(),
13: "Content-Length": buffer.byteLength,
14: "IF-MATCH": "*"
15: }
16: });
17: },
Now we have the function to read the file content and the other function to upload the content as an attachment to a list item, so next we have to chain them together to make a proper call. We do the chaining using the .done function.
1: function executeUploadAttachment (id, listname) {
2: readFile("uploadControlId").done(function (buffer, fileName) {
3: uploadAttachment(id, listname, fileName, buffer).done(function () {
4: alert("success");
5: }).fail(function () {
6: alert("error in uploading attachment");
7: })
8: }).fail(function (err) {
9: alert("error in reading file content");
10: });
11: }
Downloading the attachments of a list item
This is pretty straight forward. The following URL will give the relative URLs of the attachments of a list item.
_spPageContextInfo.webServerRelativeUrl + /_api/web/lists/getbytitle(‘” + listname + “’)/items(‘” + id.toString() + “’)/AttachmentFiles
1: function getAttachments (id, listname) {
2: return $.ajax({
3: url: _spPageContextInfo.webServerRelativeUrl + "/_api/web/lists/getbytitle('" + listname + "')/items('" + id.toString() + "')/AttachmentFiles",
4: type: "GET",
5: contentType: "application/json;odata=verbose",
6: headers: {
7: "Accept": "application/json;odata=verbose"
8: }
9: });
10: }
Use the following code snippet get the output.
1: getBillingAttachments(1, "mylist").done(function (data) {
2: var result = data.d.results;
3:
4: for (var i = 0; i < result.length; i++) {
5: alert(result[i].ServerRelativeUrl);
6: }
7: })