Last post….

Hi,

Unfortunately, I’ll no longer post on this blog. I’ve refocused my career on a different direction and I’m no longer working directly with SharePoint. I’ll leave the blog up and running for now since I still can help some people with some SharePoint issues.

Yours,

Andy.

Force SharePoint 2010 Search Scope Update

For those wondering how to force a scope update and not having to wait 14 minutes for each update, this can help.

  • Go to Central Administration site
  • Go to your Search Service Application (Manage Services -> Search SA)
  • On the left hand side, click on Search Administration link under Administration
  • Unders System Status, look for an entry saying Scopes needing update and click on the Start Update Now link (see below)

Pretty straightforward !

Hope that helps !

Andy Nogueira.

Access Denied Messages when retrieving SharePoint User Profiles Count even running in Elevated code

This is another tricky one. And I think I had this problem long time ago which I had this workaround but couldn’t remember about it until I’ve looked into an old code snippet.

Here’s the scenario.

You need to retrieve the total number of user profiles in SharePoint. The API has a property for that in the UserProfileManager class. You could just write some code like this:


UserProfileManager profileManager = new UserProfileManager(serviceContext);
long ProfileCount = profileManager.Count;

But the problem is that in order to retrieve this you need to have admin privileges on the User Profile Service. So the logical way of doing this is to run the code with Elevated privileges and ensure the identity used by the application pool of your site has admin privileges on the User Profile service. So I’ve tried that using the code below:


SPSite siteColl = SPContext.Current.Site;

try{
  SPSecurity.RunWithElevatedPrivileges(delegate()
  {
    using (SPSite ElevatedsiteColl = new SPSite(siteColl.ID))
    {
      SPServiceContext serviceContext = SPServiceContext.GetContext(ElevatedsiteColl);
    UserProfileManager profileManager = new UserProfileManager(serviceContext);
    ProfileCount = profileManager.Count;
    }
  });
}
catch (Exception ex)
{
  LogException(ex);
}

Testing the code running under an Admin account it was fine (because it was the same account used by the site’s application pool). But when I tested the code using a regular user this code should still run fine (because I was running it elevated). Unfortunately that’s not what happened. For some weird reason seems that the SharePoint API was trying to impersonate the current user thus throwing an exception and showing an Access Denied error which said  Access Denied: Only an administrator may retrieve a count of all users.

So after sleepless nights (just kidding it was just some banging my head on the wall), I finally remembered to take a look at an old code snippet that I had when facing the same issue in the past, and I’ve decided to write this post (blog posts are a great way to use as a diary).

The Workaround

Basically my workaround is to set the current HttpContext to null inside the code, but keeping the existing context in a temp variable so I can revert it back once I run the snippet. You have to revert it back to the original context otherwise you are going to get a lot of errors. The code looks like this: 

SPSite siteColl = SPContext.Current.Site;
HttpContext tempCtx = HttpContext.Current;

try
{
SPSecurity.RunWithElevatedPrivileges(delegate() {
using (SPSite ElevatedsiteColl = new SPSite(siteColl.ID))
{
SPServiceContext serviceContext = SPServiceContext.GetContext(ElevatedsiteColl);
HttpContext.Current = null;
UserProfileManager profileManager = new UserProfileManager(serviceContext);
ProfileCount = profileManager.Count;} });
}
catch (Exception ex){ LogException(ex);}
finally{ HttpContext.Current = tempCtx;}

Using the code above I could retrieve the count even using a regular user (no admin access) .

 I hope this saves some time on your side and avoid some head banging on the wall

Have a nice one !

Andy Nogueira.

SPWeb.CurrentUser returns SHAREPOINT\System not the real user name.

If you try to get the current user login name or name in SharePoint and if it shows SHAREPOINT\System account, that’s because the current logged user is an admin account and is probably the one used in the application pool of the site. Also, you are probably getting the current user from an elevated SPWeb inside a RunWithElevatedPrivileges code. You can use the snippet below to get the real user:


SPWeb site = SPContext.Current.Web;
SPSecurity.RunWithElevatedPrivileges(delegate()
{
  using (SPSite ElevatedsiteColl = new SPSite(siteColl.ID))
  {
    using (SPWeb ElevatedSite = ElevatedsiteColl.OpenWeb(site.ID))
    {
      //Don't use the ElevatedSite.CurrentUser
      string currUser = site.CurrentUser;
    }
  }
});

This will show the real login name instead of SHAREPOINT\System

Bear in mind that the code above is just a snippet and to show you the idea. Please make sure you use the SharePoint best practices coding for disposing objects when using the snippet above.

Hope that helps !

Changing namespace in Visual Studio 2010 might break a SharePoint 2010 webpart project

Just want to create a post about this since it’s the second time this happened to me and I wished this second time I had created this post when I experienced this error for the first time so I could check my own blog and figure out what was happening. Blogs can be used as journals too for our own help :-)

I was creating a SharePoint 2010 project in Visual Studio 2010. I’ve selected the Empty Project and then Add New Item and selected the Webpart item (not the Visual Webpart). After doing some coding, for some reason I’ve decided to change the original namespace that Visual Studio had created for me on the webpart class (.cs file). Then I did some more coding and time to test it. I right click on the project name and select Deploy (I love this new feature in VS2010). Everything goes smooth, package is deployed and everything seems fine. So I go to my SharePoint site, Edit the page, Insert a Webpart, select my new custom webpart and when I hit the Add button, for my surprise I got the error below.

And this is the second time around that this happened to me. The first time was a long time ago so I couldn’t remember why. Then it’s time to do some troubleshooting. I’ve verified that the .DLL file was in the GAC, I’ve checked the web.config file to make sure a <SafeControl> entry was created. Everything looks good. Then I check the webpart definintion file in the WebParts gallery and closely looking at the XML I’ve noticed that the namespace was not matching with my webpart class. The original namespace was still showing. So I went back to my Visual Studio project and I’ve opened the .webpart file (see below) that was created for me.

And for my surprise the original namespace was still showing up there. So if you change your namespace after you create a project in VS2010 make sure that in the .webpart file (see below) under the <Metadata> <type> elements, the name attribute has the correct namespace.


<?xml version="1.0" encoding="utf-8"?>
<webParts>
<webPart xmlns="http://schemas.microsoft.com/WebPart/v3">
<metaData>
<type name="SP2010.WebParts.MembesListingWebPart.MembersListingWebPart, $SharePoint.Project.AssemblyFullName$" />
<importErrorMessage>$Resources:core,ImportErrorMessage;</importErrorMessage>
</metaData>
<data>
<properties>
<property name="Title" type="string">Members Listing WebPart</property>
<property name="Description" type="string">This WebPart lists the members of a site</property>
</properties>
</data>
</webPart>
</webParts>

Another change you have to do and this one is a tricky one is on the Visual Studio 2010 SharePointProjectItem.spdata file. This is a file I believe Visual Studio uses internally to package and deploy the solution. But the catch is that it doesn’t show by default, so you have to click on the “Show All Files” button in the Solution Explorer and this file will show inside your WebPart folder (see below). Edit the file and change the Namespace attributes according to your new namespace.

Also, don’t forget in that if you change the namespace, in your project properties, make sure it’s reflected in the Default Namespace field in the Application tab of your Project properties (right-click your project name and select properties).

Hope this will help some people save some troubleshooting time !

Manage Access Requests not showing on a SharePoint 2010 site

The other day I was just trying to get to the Manage Access request option on SharePoint 2010 and for my surprise I couldn’t find the link to get to the page.

So in order to figure it out, I went to a MOSS 2007 site, and I knew I could get to it going to Site settings -> Advanced permissions -> Settings -> Access requests, this showed me that this page name and location was /_layouts/setrqacc.aspx. I thought that Microsoft probably haven’t changed this on SharePoint 2010. So I went back to my SP2010 server and appended this location to my site’s URL. For my surprise I got an error message that gave me an insight on what was going on. The message said something about emails not being configured.

So I went to the SharePoint 2010 Central Admin site, and under System Settings -> Configure outgoing e-mail settings, once I configured the smtp server and outgoing email.

Then I tried to access the page again and it worked. I’ve also realized that one option in SharePoint 2010 that I was not seeing before started to show up, and that was a link on the Ribbon going to Site Settings -> Site Permissions. The link that said Manage Access Requests (see below) started to show up.

SilverPart 2.1 release, a SharePoint webpart to expose Silverlight applications

I’ve just released a new update of the SilverPart on CodePlex. For those who don’t know this is an open source webpart I’ve created some time ago and it allows you to run Silverlight applications in WSS 3 and MOSS 2007.

SharePoint 2010 comes with a webpart like this OOTB, but in the old SharePoint (2007) this was not available. The nice thing about it was that I’ve created it in a way that you didn’t have to install additional software such as the ASP.NET Silverlight control.

This interim release 2.1 fixes some reported issues with using it with Firefox and anonymous access.

You can download it from http://silverpart.codeplex.com

Cheers

Andy Nogueira

P.S – What I really liked about CodePlex is that now you can insert Ads on their page and I’ve opted to donate the Ad revenue, so I’m not only giving back to the community but I’m also helping a good cause.

Twitter and Facebook compared to Sharepoint social model

Just got a message that a post I’ve created on my company’s blog some time ago has been active recently in Twitter. It compares Sharepoint network model with Toronto and Facebook. Here’s the link to the post

http://www.nonlinearcreations.com/blog/index.php/2009/09/01/sharepoint-social-model-more-similar-to-twitter-than-other-social-networking-sites/

Thanks

Andy Nogueira

Having fun with the new LINQ to SharePoint on SharePoint 2010 (SP2010)

Introduction

This will be my first post on the new LINQ to SharePoint feature available in SharePoint 2010. I’ve decided to give it a try. I thought that it would be so much easier for me to retrieve SharePoint information using LINQ than creating CAML code since I’m very familiar with LINQ and used it a lot of times, especially LINQ to SQL and LINQ to Objects. But this previous knowledge on LINQ also played some tricks on me since that usually we tend to take a lot of things for granted when dealing with new technologies. So, here’s how I’ve started.

First I’ve watched one of the SharePoint 2010 Developer videos on Channel 9 related to LINQ to SharePoint. This was a good overview about the technology with a good demo. Then I’ve followed the walk-through on the SharePoint 2010 book that was distributed at the SharePoint Conference 2009. The walk-through is the one on page 162 called “Using LINQ to SharePoint from within a Visual Web Part”. That also gave me a better insight and a nice idea on how to use it in a Visual WebPart.

So, the first thing you need to do to use LINQ to SharePoint is to generate a mapping layer (same idea as LINQ to SQL) where you can have your SharePoint list definitions generated as C# (or VB) .NET classes. That will give you strongly-typed classes of your SharePoint schema. Again, just keep in mind that if you do change your SharePoint list definition you will probably need to re-generate this mapping layer. In order to generate this, you have to use a tool called SPMetal

Step 1 – Using SPMetal to generate a mapping layer

The tool SPMetal is installed as part of the SharePoint 2010 installation and it’s located by default at “C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\14\BIN”. If you open a command prompt, go to that folder and type spmetal, it will show you a description of its valid parameters. There’s also a good article on MSDN about SPMetal.

Basically the main parameters are the site URL, the namespace, the filename and the type of file (.cs or .vb). Here’s an example:

c:\>SPMetal /web:http://localserver/team /namespace:MyCompany.Data /code:TeamSite.cs

This command will basically generate a CSharp file where I can import into your Visual Studio 2010 project.

Step 2 – Using a parameters file to override the SPMetal default rules

There is also an additional option in SPMetal called parameters where you can specify a XML file that allows you to override the default rules to generate the mapping layer. So let’s say you want to specify which lists you want in your mapping file. You can use for example a file called myParameters.xml (it can be any filename as long as you specify the name right on the command-line).

c:\>SPMetal /web:http://localserver/team /namespace:MyCompany.Data /code:TeamSite.cs /parameters:myParameters.xml

The first time I’ve tried to use a parameters file, I’ve got a bunch of errors trying to generate the file. Some of these errors were related to a copying and paste problem from the MSDN article to my file. So make sure you use a valid XML editor instead of Notepad because the double quotes can play a trick on you. By using a XML editor you can guarantee that there are no malformed XML in your parameters file.

Also, make sure you understand the right schema for the parameters file. In the beginning I’ve also had problems because I was putting the XML elements in my file in an invalid order. Also, make sure that you understand what elements are parents and children of each other. It took me some trial and errors until I could figure it out, but it’d have saved me sometime if I had found earlier the really nice MSDN article describing the whole parameters file schema (see below)

These  two articles are a must read to be able to come up with a nice parameters  XML file

Overriding SPMetal Defaults with a Parameters XML File

SPMetal Parameters XML Schema

So let’s say you have a list in SharePoint in your site called “Customer”. Let’s assume that you are not using any custom Content Type on that list (assuming in this case it’s a pretty vanilla custom list). If you want to generate a mapping layer that will have only the Customer list and you want spmetal to generate fields for some out-of-the-box SharePoint fields such as the Author and Created you can (see below). There’s also a parameter called <ExcludeOtherLists> that tells SPMetal to generate classes for only the lists that you’ve specified. That can be pretty handy in case you don’t want to have a huge mapping layer file. So here’s an example:

myParameters.xml

  <?xml version="1.0" encoding="utf-8"?>
  <Web AccessModifier="Internal" xmlns="http://schemas.microsoft.com/SharePoint/2009/spmetal">
    <List Name="Customer">
      <ContentType Name="Item" Class="Customer" >
        <Column Name="Author" Member="Author" />
        <Column Name="Created" Member="Created" />
        <Column Name="Description" Member="Description" />
      </ContentType>
    </List>
    <ExcludeOtherLists />
  </Web>

Once the file is generated you can go to your project in Visual Studio 2010 (I’m assuming that you’ve already created one of the SharePoint 2010 project templates such as the Visual WebPart one) and add the file to your project by righ-clicking on your project name and selecting Add | Existing Item. Browse to the folder where you generated the file, select it and click Add.

Add Item in Visual Studio

Step 3 – Adding LINQ to SharePoint references

Rigth-click on your project again and select Add Reference. The Add Reference window will show up.Just select the Microsoft.SharePoint.Linq.dll

Once the Microsoft.SharePoint.Linq.dll is referenced then you need to add the following using statements on your code (if you didn’t generate the mapping layer with the same namespace as the class namespace where you will be using it, then you have to add this namespace too).


using System.Linq;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Linq;
using MyCompany.Data;  /* My mapping layer namespace */

Now that you have your mapping layer and the required references in place it’s now time to have some fun. Let’s get our hand dirty with some Linq code.

Step 4 – Retrieving SharePoint information using Linq

If you open your mapping file (in my case TeamSite.cs) you will see that SPMetal created a DataContext class for you and it should look like this

internal partial class TeamSiteDataContext : Microsoft.SharePoint.Linq.DataContext {}

You can also see that for the list that you’ve specified (in my case Customers) there was also a member created for that in this class, something like

[Microsoft.SharePoint.Linq.ListAttribute(Name="Customers")]
public Microsoft.SharePoint.Linq.EntityList<Customer> Customers{}

Now the fun part. In order to retrieve Customers from SharePoint I need to instantiate a DataContext class, load the list and iterate the items. You can use something like this code below in your WebPart code-behind or Visual WebPart User Control (ascx) code-behind.

try{
 using(TeamSiteDataContext ctx = new TeamSiteDataContext(SPContext.Current.Web.Url))
 {
  ctx.ObjectTrackingEnabled = false; //this is good for performance if you are only retrieving information
  EntityList<Customer> Customers = ctx.GetList<Customer>("Customers");
  var query = from c in Customers.ToList()
              select c;
  foreach(var cust in query)
  {
    //Do something here. The objects are strongly typed so I could do something like cust.Name for example
  }
 }

This MSDN link has some additional details on how to use this and have a few more examples.

Gotchas and Limitations

While “playing” with LINQ to SharePoint I’ve tried to do “wild” things that were pretty common in LINQ to SQL such as joins. So when I mentioned in the beginning of this post that you should never take things for granted, believe me this is one of this cases. There are some limitations in what you can do with LINQ to SharePoint and some LINQ constructs are not even possible. There are some that are possible but are called “inefficient”. Make sure you read this article first before trying to do “wild” things: Efficient, Inefficient, and Unsupported LINQ Queries

I’ve tried to do some joins in my LINQ based on two SharePoint lists linked by a lookup field but I’ve got a strange error message saying something about that Inneficient Queries were not allowed and I should change a property on my DataContext. Reading the article above (on Step 4) it says that you should set a property called AllowInefficientQueries() to true but I couldn’t find this property in my DataContext class. I’ve searched the web and found some people saying that as of Beta2 this is not there anymore, so I’m assuming this was in a previous beta but the documentation was not updated accordingly (but this needs to be confirmed).

Conclusion

LINQ to SharePoint is very promising and it can speed up things a lot if you need to retrieve and update information in SharePoint. It’s a great alternative to creating custom CAML code and it might leverage some of your existing knowledge in LINQ especially if you already done a bunch of them. If you haven’t then a good LINQ book (but doens’t cover LINQ to SharePoint) is Pro Linq from Apress.

Hope that helps and have fun coding with LINQ to SharePoint in SharePoint 2010 !

Cheers,

Andy Nogueira.

Links not enabled on SharePoint 2010 Central Administration Site

Here’s a quick tip that may save some people a lot of time. I have a standalone SharePoint 2010 environment installed on my desktop for development purposes (Vista 64-bit). I was trying to create a new web application to host my site but for my surprise when I went to Central Administration -> Application Management -> Manage Web Applications, the ribbon wouldn’t show some of the buttons enabled (see image below). When I clicked on one of the web applications I saw only a few buttons on the ribbon enabled. That was strange because I was pretty sure I’m a farm administrator.

While doing some research on what might be causing this problem I’ve realized that I had to access the Central Admin site in a different way. So this is what I did.

  • Please make sure to add the Central Administration site to the Intranet zone
  • Run Internet Explorer as Administrator (right-click the icon and select Run as administrator)
  • Not sure if this makes a difference, but I’ve also used the IE 64-bit version

Once I’ve did that I’ve tried to access the site again, using the same login credentials and voilá. For my surprise some of the buttons that were disabled before this time were enabled (see image below). And I was able to click on New button to create a new web application.

Hope that this can save some people some time.

cheers,

Andy Nogueira