Have you ever wanted to grab all of the user profile photos in your SharePoint environment, whether it was to make sure none of them were inappropriate or just to have a laugh at some of the creativity? It can be pretty entertaining, even if you don’t have an HR-ish reason for wanting to check on them.
I was recently asked to put together some way for a small group of users to easily look through all the pictures that had been uploaded. The idea was for this to work from a client machine with no server-side installs would be needed. This meantusing the object model was out (no Client OM in MOSS remember). Fortunately in this environment all the user profiles are indexed to enable the “People search” capability, so the search web service is a handy and performant way to grab a few profile attributes for all the users who have submitted a profile.
I started by figuring out the syntax of the query I wanted to use to get the results back. If you don’t already use it, I can’t recommend the SharePoint Search Service Tool enough. The standalone executable is a free download from Codeplex that some really sharp people from Microsoft were kind enough to share, and it’s a very educational and useful tool if you want to dig into the SharePoint search engines native language a bit. Generally I find I can just pick the scope and first few attributes I want to include in the results and then tweak the query syntax by hand. One of the most powerful aspects is that the search tool lets you use SQL Syntax for the queries, which opens up a whole bunch of possibilities that the OOTB search web parts can’t do. In the case, the crux of the query was to use the “People” scope, pick the attributes I wanted”, and make sure I only grabbed profiles that actually had a PictureURL populated. You might think you’d be able to do something like PictureURL is not null, but despite being legitimate syntax it doesn’t appear to actually work. For my purposes, I just ended up a “like (h%)”, which got the job down even though it may not be the most efficient predicate ever.
At this point, I had a nice chunk of XML for the QueryPacket to send to the search web service, as well as a pretty good idea of what the XML in the response was going to look like. I don’t claim to be an XSLT master, but it’s not rocket science to turn the XML response into a really simple HTML page that shows the thumbnail versions of all the images, especially if you have a nice XML/XSL editor at your disposal to help with debugging. Using the auto-generated thumbnails is highly recommended, by the way, unless you like seeing your browser sweat bullets trying to layout thousands of 100K-5MB images on a single page. Like I mentioned before, it’s pretty funny what people will upload even though it all ends up in a 150×150 square.
I now had a one-off version of the desired result, but didn’t want to want to burden the actual customers with needing to know how to use things like the Search Service Tool, even as much as I like it. I needed something quick and easy to automate this process, and for most SharePoint folks these days “quick and easy automation = PowerShell”. After saving the QueryPacket XML and .xsl file for transforming the response, I just need a handy way to call the search web service from PowerShell. At first I used the “old school” method of just generating and compiling a proxy stub with wsdl.exe and calling that from PowerShell. After a bit more search engine fun, I found that there is a New-WebServiceProxy cmdlet built into Powershell to handle this for you.
Now I have 3 easy-to-distribute text files, and as long as the user can run the PowerShell installer, which is pretty straightforward, they can just unzip the files, right-click the .ps1 to choose “Run with PowerShell”, and enjoy perusing a large HTML file with a bunch of images that link back to the user profile page. The actual HTML could be made much fancier, and obviously you may care about a different set of profile properties than I’m pulling.
This was a fun little exercise that actually served a practical purpose in this case, but might otherwise be a nice, fun page to show a client for whom you’ve deployed SharePoint My Sites. You can download and play with the source files however you wish. I’d love to hear feedback, or other ways to extend this idea in the comments.