Tuesday 4 August 2015

Execution of a CAML query by means of a POST method type REST call to get list view data in the Host Web from App Web


Few days ago, We faced a requirement from our client. The requirement was to read a SharePoint listview in the host web from app web. As we all know, view is just a query on a list maintaining certain conditions. It has no physical existence. So the challenge was to get those data from list by maintaining certain conditions.

As we want to get data from a list, so the primary thinking was to read data by means of a GET 
method call using REST API. But we didn't get such method to find a solution of this problem.


The following method illustrates the scenario:

 function getListItemsForView(webUrl, listTitle, viewTitle)
{
        
        
        $.when(getJson(webUrl, listTitle, viewTitle)).then(function (data)
            {
                var viewQuery = data.d.ViewQuery;
                return getListViewItems(webUrl, listTitle, viewQuery);
            });
    }


The idea is to get the view query by means of a GET method call as follows:

 function getJson(appweburl, listname, viewTitle) 
{
        
        var d = $.Deferred();
        var datalist = null;
        var executor;

        executor = new SP.RequestExecutor(appweburl);

        executor.executeAsync({
            url: appweburl + "/_api/SP.AppContextSite(@target)/web/Lists/getbytitle('" + listname + "')/Views/getbytitle('" + viewTitle + "')/ViewQuery?@target='" + _hostWebUrl + "'",
            method: "GET",
            headers: {
                "content-type": "application/json; odata=verbose"
                "Accept": "application/json;odata=verbose"
            },
            success: function (data) {
                if (data.body != null ) {
                    datalist = JSON.parse(data.body);
                }
                d.resolve(datalist);
            },
            error: function (data, errorCode, errorMessage) {
                d.reject(errorMessage);
            }
        });
        return d.promise();
    }


Then we need to POST the view query  in JSON format to get the view data as list items.

function getListViewItems(appweburl, listTitle, queryText)
 {
        var viewXml = '<View><Query>' + queryText + '</Query></View>';      
        var queryPayload = {
            'query': {
                '__metadata': { 'type': 'SP.CamlQuery' },
                'ViewXml': viewXml
            }
        };
        
        
        var d = $.Deferred();
        var datalist = null;
        var executor;
        executor = new SP.RequestExecutor(appweburl);
        executor.executeAsync({
            url:  appweburl + "/_api/SP.AppContextSite(@target)/web/lists/getbytitle('" + listTitle + "')/getitems?@target='" + _hostWebUrl + "'",
            method: "POST",
            body: JSON.stringify(queryPayload),
            headers: {
                        
                        "Accept": "application/json; odata=verbose",
                        "content-type": "application/json; odata=verbose"
                    },
            success: function (data) {
                if (data.body != null ) {
                    datalist = JSON.parse(data.body).d.results;
                }
                
            
                d.resolve(datalist);

               

            },
            error: function (data, errorCode, errorMessage) {
                d.reject(errorMessage);
            }
        });
   
        return d.promise();
        
    }

Actually above method call is returning the result of the view query from the list
passed by the listTitle parameter like shown below:

<View><Query><Where><Eq><FieldRef Name="My_x0020_Column" /><Value Type="Text">01</Value></Eq></Where></Query></View>

So the trick is the execution of a CAML query by means of a POST method type REST call to get view data.



Happy SharePointing..................:)