SP2010 Add/Update multi-select lookup column REST
-
10-10-2020 - |
Question
I have a list named CAG_QUESTION with a multi select lookup column to a list named CAG_REFERENCES. I have been unable to get an update to work that includes the lookup column. I thought I needed to pass an array of the CAG_REFERENCES Ids.
Here is the code I have.
var itemProperties = {
ReferenceLookup: {
results: [{
"__metadata": { type: "Microsoft.SharePoint.DataService.CAG_REFERENCESItem" },
Id: 33
},
{
"__metadata": { type: "Microsoft.SharePoint.DataService.CAG_REFERENCESItem" },
Id: 23
}]
}
};
updateListItem(myWebUrl(), "CAG_QUESTION", 184, itemProperties,
function() {
console.log('Success Guardian ... Success.');
},
function(error) {
console.log(JSON.stringify(error));
}
);
It fails with a payload must represent a valid array format for collections error.
{"readyState":4,"responseText":"{\r\n\"error\": {\r\n\"code\": \"\", \"message\": {\r\n\"lang\": \"en-US\", \"value\": \"Error processing request stream. The payload must represent a valid array format for collections.\"\r\n}\r\n}\r\n}","status":400,"statusText":"Bad Request"}
Solution
Its sad this was never answered here. But for the lurkers here it is.
Adding selections to a multivalue lookup field using REST
Here's the necessary format for your data payload:
var data = JSON.stringify({
MultiLookupColumnName:[
{
__metadata: {
uri: "http://yoursiteurl/_vti_bin/ListData.svc/LookupListName(1)"
}
},
{
__metadata: {
uri: "http://yoursiteurl/_vti_bin/ListData.svc/LookupListName(2)"
}
}
]
});
This example assumes that your lookup column is named MultiLookupColumnName
, that the list that your lookup column is looking up against is entitled LookupListName
, and that you want to set your multi-lookup field to lookup to the items with IDs 1 and 2.
In your code, you would use that data
variable in place of your itemProperties
variable.
For the sake of completeness, here's a full example without jQuery:
var idOfItemToUpdate = 1;
var url = "/serverRelativeUrl/_vti_bin/ListData.svc/YourListName("+idOfItemToUpdate+")"
var data = JSON.stringify({
MultiLookupColumnName:[
{__metadata:{uri:"http://yoursiteurl/_vti_bin/ListData.svc/LookupListName(1)"}},
{__metadata:{uri:"http://yoursiteurl/_vti_bin/ListData.svc/LookupListName(2)"}}
]
});
var xhr = new XMLHttpRequest();
xhr.open("POST",url,true);
xhr.setRequestHeader("X-HTTP-Method", "MERGE");
xhr.setRequestHeader("If-Match", "*");
xhr.setRequestHeader("Content-Type","application/json");
xhr.send(data);
Removing selections from a multivalue lookup field using REST
Note that to remove a value from the multi-selection lookup field, you'll need to use a different operation. The above operation only adds to the selected values.
To remove a selected value from the field, use a DELETE
operation like so:
var xhr = new XMLHttpRequest();
xhr.open("DELETE",
"/serverRelativeUrl/_vti_bin/ListData.svc/YourListName(1)/$links/MultiLookupColumnName(2)",
true);
xhr.send();
That code would remove the lookup value with an item ID of 2 from the field named MultiLookupColumnName
on the item with an ID of 1 on the list named YourListName
.
(Can you diagram that sentence?)
Footnote: Callback functions without jQuery
I used XMLHttpRequest
for the above examples, but I don't want that to cause you any headaches down the road.
If you decide to use the built-in XMLHttpRequest
instead of a jQuery/AJAX wrapper, you can use its onreadystatechange
event and pass it a callback function like so:
xhr.onreadystatechange = function(){
if(xhr.readyState == 4){
myCallbackFunction(xhr.status, xhr.responseText);
}
};
function myCallbackFunction(status, text){
// decide what to do based on the status
}
This answer brought over from Stack where it was answered by Thriggle