36

SharePoint 2013 CSOM API contains the following methods for accessing List object:

For example:

var listTitle = "Tasks";
using(var ctx = new ClientContext(webUrl))
{
     var list = ctx.Web.Lists.GetByTitle(listTitle);
     ctx.Load(list);
     ctx.ExecuteQuery();
}

From another hand, SSOM API contains SPWeb.GetList method to gets the list that is associated with the specified server-relative URL.

The question is: how to effectively load List by server-relative URL in CSOM?

  • 1
    Vadim, if you had mention using another method other than CSOM, then yes. The SOAP services has it a method that you can use - SiteData.GetURLSegments. I wrote about it here: paultavares.wordpress.com/2014/02/18/… – Paul T. Sep 30 '14 at 19:19
  • ListCollection lists = context.Web.Lists; context.Load(lists, all => all.Include(l => l.RootFolder)); It does not work either! – ananda May 27 '17 at 8:05
28

This seems to be pretty close in performance:

context.Load(lists, all => all
  .Where(l => l.RootFolder.Name == "MyListUrl")
  .Include(l => l.Id));
context.ExecuteQuery();
list = lists.Single();

If you need to get this by server-relative url you would need to parse the web url and list url first.

  • 1
    Had to take some performance tests away from the answer because of high variance. Anyways there doesn't seem to be big difference in performance (~0-25%). – thomius Sep 30 '14 at 13:16
  • 1
    Cool, also added an extension method here: Not so pretty with all the parsing.. – thomius Sep 30 '14 at 15:03
  • Took the extension method away because didn't invent how to protect against user giving a subfolder as an argument (instead of the actual list/library RootfolderName), without executing query more than once. – thomius Sep 30 '14 at 15:38
30

For those who are still looking for the answer. SharePoint 2013 (since SP1 at least see UPD below) contains special method Web.GetList. It accepts site-relative url for the list, i.e. site/dev/lists/mylist.

Sample code for .NET object model:

var ctx = new ClientContext("http://sp2013dev/sites/dev");
var list = ctx.Web.GetList("sites/dev/lists/Addresses");
ctx.Load(list);
ctx.ExecuteQuery();    
Console.WriteLine(list.Title);

The same situation for JavaScript object model (except the fact that msdn documentation is lacking and you don't find this method here at the moment of writing this, May 2015):

var context = SP.ClientContext.get_current();
var list = context.get_web().getList("/sites/dev/Lists/Addresses"); 
context.load(list);
context.executeQueryAsync(function() { 
    alert("loaded!"); 
    }, function() { 
    alert("failed!"); 
});

Now we don't need all this hacks with folder or list properties.

UPD:

Just tested that this method is not included in SP1. It works starting from February 2015 CU (sorry, can't check the exact CU number)

  • Oh, finally, i suppose it should be considered as the most accurate answer then.Thanks! – Vadim Gremyachev May 6 '15 at 13:05
  • I couldn't find this method in the latest NuGet download of the DLL. Instead, I found an version of the DLL on my dev server (patched to March 2015 CU) but it didn't work for Production which is only SP1. – PeterX May 14 '15 at 4:51
  • @PeterX, you're correct, unfortunately SP1 doesn't contain this method, I've already mentioned it. It seems it was included at the end of 2014 or at the beginning of 2015. – Sergei Sergeev May 14 '15 at 8:37
  • I can confirm that it also works with absolute urls – Kirschi Aug 10 '16 at 8:32
  • 1
    And as it's included in the CSOM, now the REST endpoint are also updated: _api/web/getList('/sites/yoursite/yourlibraryOrList') – dbardakov Jan 26 '17 at 12:12
18

Yet another version to load List by server relative Url using CSOM.

The solution consists of the following steps:

  1. Retrieve list Folder object using Web.GetFolderByServerRelativeUrl method
  2. Retrieve List by specifying List ID stored in vti_listname property from Folder.Properties object

Code:

static class WebExtensions
{
    /// <summary>
    /// Load List by server relative Url
    /// </summary>
    /// <param name="web"></param>
    /// <param name="listUrl"></param>
    /// <returns></returns>
    public static List LoadListByUrl(this Web web, string listUrl)
    {
        var ctx = web.Context;
        var listFolder = web.GetFolderByServerRelativeUrl(listUrl);
        ctx.Load(listFolder.Properties);
        ctx.ExecuteQuery();
        var listId = new Guid(listFolder.Properties["vti_listname"].ToString());
        var list = web.Lists.GetById(listId);
        ctx.Load(list);
        ctx.ExecuteQuery();
        return list;
    }
}

Usage

using(var ctx = new ClientContext(webUrl))
{
    ctx.Credentials = new SharePointOnlineCredentials(userName,securePassword);
    var tasksList = ctx.Web.LoadListByUrl("Lists/Tasks");
    Console.WriteLine(tasksList.Title);
}

Cons:

  1. Only SharePoint 2013 CSOM is supported
  2. Requires two separate requests to server
  • 1
    Nice usage of out-of-the-box methods, and no need to parse server-relative url. – thomius Sep 30 '14 at 15:06
  • 1
    Also you can use rest api to get list id instead of relying on property bags: http://sharepoint/_api/web/lists/?$expand=RootFolder&$filter=RootFolder/ServerRelativeUrl eq '/Lists/MyCoolList'&$select=ID. It also should reduce client-server traffic – Sergei Sergeev Mar 19 '15 at 10:55
  • I get the error Error 2 'Microsoft.SharePoint.Client.Folder' does not contain a definition for 'Properties' and no extension method 'Properties' accepting a first argument of type 'Microsoft.SharePoint.Client.Folder' could be found (are you missing a using directive or an assembly reference?) any thoughts? – PeterX May 14 '15 at 4:06
  • I had an out-of-date Microsoft.SharePoint.Client DLL. I couldn't find any MS downloads and the NuGet installer seemed to have a bug, so I harvested the DLLs from the NuGet download and added the references manually. – PeterX May 14 '15 at 4:30
  • 1
    I now get a ServerException / File Not Found. error, using either an absolute URL or a relative URL. – PeterX May 14 '15 at 4:36
2

I unfortunately couldn't get any of the above working, so I used an ugly hack:

public static List GetListByUrl(ClientContext context, string listUrl)
        {
            List result = null;

            ListCollection lists = context.Web.Lists;
            context.Load(lists, all => all.Include(l => l.RootFolder));            
            context.ExecuteQuery();

            string listUrlPartial = new Uri(listUrl).PathAndQuery.ToLower().Replace("%20", " ");
            foreach (List list in lists)
            {
                string thisListUrlPartial = list.RootFolder.ServerRelativeUrl.ToLower().Replace("%20", " ");
                if (listUrlPartial.StartsWith(thisListUrlPartial))
                {
                    result = list;
                    break;
                }
            }

            return result;
        }

Of course, your mileage will vary. Recommend upgrading to latest SharePoint patch to get the new method (as per @Kai's answer), but unfortunately I don't have that option at the moment.

0

I do not have SP1 for my SharePoint, but this worked for me:

var clientContext = new SP.ClientContext("absolute url to sites that contains the list");

var IssueList = clientContext.get_web().get_lists().getByTitle("title of the list");
New contributor
Kelvin Hu is a new contributor to this site. Take care in asking for clarification, commenting, and answering. Check out our Code of Conduct.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.