Get list of users from Active Directory using SPServices

Jul 27, 2012 at 1:19 PM

Hi,

I'm building a replacement Sharepoint absence tracker app, where I hope to use SPServices to dynamically build reports, based on one or more lists on the site.

The challenge I have is this: I need to find a way to retrieve a list of users in the site, based on their department name, so that I can then iterate through a second list (already on site), and perform a match against that list, to find out if that user was present or absent on anyone day during a given week.

The constraints I'm working to are:

1. Using the User Information list at each site collection would work, but I'v not found any example code that shows how to query for *all* users in a specific department, and not just a specific user. I need to get basic details for them, but there may be opportunities later to get details such as their picture. I'm also hoping not to have to manually add in permissions for named users if possible, so I can make the system self-maintaining.

2. I need any answer to be based around jQuery, so I can either edit the page using Sharepoint Designer, or put the code into a CEWP on the page. I am keen to avoid C# solutions where possible, due to support constraints that will come into force soon.

Can anyone please help with any tips or examples of how I can (a) generate the user list as above, and (b) iterate through this list, to match up with any instances of absences that are recorded in a Sharepoint list?

Thanks!

 

Coordinator
Jul 30, 2012 at 8:27 PM

You can query the User Information List just like any other list, assuming you have permissions to do so. It's simply a hidden list in the root site of the Site Collection. Keep in mind that only users who have "touched" the Site Collection in some way will be in the list, however.

M.

Jul 31, 2012 at 7:48 AM

Hi,

Thanks for this - based on what I've found so far, it does look like I'm not going to be able to pull the information from Active Directory that I want, and I will have to use the User Information List. I will have a try with the User Information List, and see if I can get any results - I will let you know how I get on.

 

Jul 31, 2012 at 9:28 AM

Hi,

I've been playing with GetListItems and the User Information List, to see if I can get names back - unfortunately everything I've tried doesn't seem to work for me? Here's the code I have so far:

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js" type="text/javascript"></script>  
 
<script type="text/javascript" src="http://cdnjs.cloudflare.com/ajax/libs/jquery.SPServices/0.7.1a/jquery.SPServices-0.7.1a.min.js"></script>  

<script type="text/javascript">

$(document).ready(function() {
  $().SPServices({
    operation: "GetListItems",
    listName: "User Information List",
    CAMLViewFields: "<ViewFields><FieldRef Name='Picture' /></ViewFields>",
    completefunc: function (xData, Status) {
      $(xData.responseXML).find("z\\:row, row").each(function() {
        var liHtml = "<li>" + $(this).attr("ows_Name")+ "</li>";
        $("#tasksUL").append(liHtml);
      });
    }
  });
});
</script>

<ul id="tasksUL"/>

I've even tried your blog post at http://sympmarc.com/2010/03/02/query-the-user-information-list-with-jquery-and-web-services/, but can't seem to get it working either - any ideas please? I need to be able to query the list, and return each name in a format I can then reuse later on...

Thanks.

Coordinator
Jul 31, 2012 at 12:47 PM

In jQuery 1.7+, the

.find("z\\:row, row")

syntax doesn't work. Use the SPFilterNode function instead.

M,

Jul 31, 2012 at 1:10 PM

Thanks for this - I've tried it, but it is still not showing anything in my CEWP?

The code I have now is:

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js" type="text/javascript"></script>  
 
<script type="text/javascript" src="http://cdnjs.cloudflare.com/ajax/libs/jquery.SPServices/0.7.1a/jquery.SPServices-0.7.1a.min.js"></script>  

<script type="text/javascript">
$(document).ready(function() {
  $().SPServices({
    operation: "GetListItems",
    listName: "User Information List",
    CAMLViewFields: "<ViewFields><FieldRef Name='Name' /></ViewFields>",
    completefunc: function (xData, Status) {
      $(xData.responseXML).SPFilterNode("z:row").each(function() {
        var liHtml = "<li>" + $(this).attr("ows_Name")+ "</li>";
        $("#tasksUL").append(liHtml);
      });
    }
  });
});
</script>

<ul id="tasksUL"/>

It feels like I am missing something stupid, as it shouldn't be this complicated to get users back from the UI List - any more ideas?

Jul 31, 2012 at 1:54 PM

The User Information List needs to be updated with explicit "read" permissions for the users that are going to be querying it. A colleague and I dove into this a while back. He wrote down his findings. Let me see if he can chime in here and give you more info. And a side note, just because you *have* to do this for the code to work, doesn't mean you should.  I really don't know if you should or shouldn't at the end of the day.

 

Cheers,

Matt

Jul 31, 2012 at 2:00 PM

Hi Matt,

Thanks for this - the project is actually based more on finding out what the art of the possible is with SPServices, and not necessarily around building a specific site in Sharepoint. The brief was written in such a way that said if the critical part (i.e. the requirement above) wasn't possible, then it was likely that I wouldn't continue.

To confirm though - when you mention that explicit permissions have to be assigned, I assume that you are referring to named individuals, and not just using a SP or domain group that implicitly includes that individual? If this is the case, I would be even less keen on doing this, as I wouldn't want to customise our environment to that degree?

Cheers,

Alex.

Jul 31, 2012 at 2:33 PM

I have tried several methods to query site users, including those built into SPServices and a couple of my own mods.  I had never tried to query the User Information List directly before now.  What I have learned about SharePoint and web services is that some of the hidden lists aren't named as you expect.  I think that may be part of the problem.  Upon closer inspection of the User Information List, you'll see it has an internal name of "UserInfo" and likely won't respond to the common name, "User Information List."  I ran into that with another hidden list I was trying to work with.  So, I tried the following, which did return results but the results are not what you're hoping for.  The list of returned user data is quite limited.

function GetUserInfoList(){
  $().SPServices({
      operation: "GetListItems",
      async: false,
      listName: "UserInfo",
      completefunc: function(xData, Status) {
        $("#MyXMLTextBox").val(xData.responseText);
      }
  });
}
Of course, for this example to work, you need to create a <textarea> element, "MyXMLTextBox", to display the raw results.  Also, employing the SPServices function, "SPDebugXMLHttpResult()", is quite handy for analyzing returned results because it structures the data for easy viewing.
Jul 31, 2012 at 2:34 PM

If I remember correctly, we just set the list to allow reads for NT Authority/Authenticated Users. I don't remember exploring any more than that, however, it'd be nice to know what you find. :)

Cheers,
Matt 

Jul 31, 2012 at 2:55 PM

Hi all,

YESS!!! It worked! ;-)

The trick of using "UserInfo" as the list name was perfect - this is now allowing me to return values correctly from the list. This means I can now start to do what I need to do - thanks for all your help in getting there.

For reference - here's the updated code I used:

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js" type="text/javascript"></script>  
 
<script type="text/javascript" src="http://cdnjs.cloudflare.com/ajax/libs/jquery.SPServices/0.7.1a/jquery.SPServices-0.7.1a.min.js"></script>  

<script type="text/javascript">
$(document).ready(function() {
var fieldsToTRead = "<ViewFields>" +
                     "<FieldRef Name='Name' />" +
                     "<FieldRef Name='Department' />" +
                     "</ViewFields>";

  $().SPServices({
    operation: "GetListItems",
    listName: "UserInfo",
    CAMLViewFields: fieldsToTRead,
    completefunc: function (xData, Status) {
      $(xData.responseXML).SPFilterNode("z:row").each(function() {
        var liHtml = "<li>" + $(this).attr("ows_Name")+ "</li>" + 
        "<li>" + $(this).attr("ows_Department")+ "</li>";
        $("#tasksUL").append(liHtml);
      });
    }
  });
});
</script>

<ul id="tasksUL"/>

Cheers,
Alex.

Aug 1, 2012 at 8:57 PM
Edited Aug 1, 2012 at 9:54 PM

You could also try something like the following.  This is what I use on my site to get users for populating jQuery UI's Autocomplete dropdown

 

$().SPServices({
    operation: "GetUserCollectionFromSite",
    async: true,
    completefunc: function (xData) {
        var users = [];
        $(xData.responseXML).find('User').each(function () {
            var item = {},
                o = $(this);
            item.value = o.attr('ID');
            item.label = o.attr('Name');
            users.push(item);
        });
        UT.USERS = users;  // This is a global var that I use
    }
});

Slightly adapted to match what you appear to be doing. I could be wrong though...
$().SPServices({
    operation: "GetUserCollectionFromSite",
    async: true,
    completefunc: function (xData) {
        var htmlToAppend = "",
              listItem = "<li></li>";
        $(xData.responseXML).find('User').each(function () {
            var o = $(this);
            htmlToAppend += $(listItem).html(o.attr('ID'));
            htmlToAppend += $(listItem).html(o.attr('Department'));
        });
        $("#tasksUL").append(htmlToAppend);
    }
});

// This way you aren't touching the DOM everytime you need to add a new item to your list.
Aug 2, 2012 at 3:23 PM

Hi _JT_,

Thanks for posting up your alternative solutions - both were very similar to what I ended up doing, but I do like your second one, particularly as I've never really been a big fan of working out CAML statements! I will try out the second one as part of playing around with SPServices in my environment - hopefully I can adapt it for some of the other service calls I've been able to work out how to use.

Cheers,

Alex.

Sep 1, 2014 at 3:40 PM
Thanks everyone for this useful post..it helped me querying the user information list. Also, and please correct me if I am wrong, the All People view we get from here (/_layouts/people.aspx?MembershipGroupId=0) represents the people in the User Information List, so if we want to remove a user from the User Information List, we do it from this page (one of the ways).
Coordinator
Sep 2, 2014 at 1:48 PM
Yash23:

You should carefully consider whether you want to remove any user from the UIL. If there is content with that user tagged to it, it can cause issues. It's far better to simply change the permissions for the user (for example, when they leave the company).

M.
Apr 28, 2015 at 2:32 PM
Hi , Is there any way to read the users from active directory group. I am asking this because the above solution returns only active directory group names in SharePoint.
Coordinator
Apr 29, 2015 at 2:01 PM
Edited Apr 29, 2015 at 2:01 PM
mundrumk:

It's better to start a new thread rather than tacking onto such an old one.

The quick answer is "No". These two blog posts give you more details on why:
http://sympmarc.com/2011/02/16/active-directory-groups-vs-sharepoint-groups-for-user-management-a-dilemma/

M.