Avoid using SPFolder.Item cause performance issue on large lists

When you call an “SPFolder.Item” Property ; it  executes below code once on Its parent Folder (if Parent Folder is not empty). this is a kind of Caching & Indexing mechanizm .Then returning related item from index of parent folder.

….
m_FileRefDict = new Hashtable(
StringComparer.Create(CultureInfo.InvariantCulture, true /*ignoreCase*/));

foreach (SPListItem item in items) *** Thats where we creating the long SQL query.
{
m_FileRefDict[item[SPGlobal.FieldNames.strFileRef].ToString()] = item;
}
….

And the code has to be like that . For Large lists ; in the Sitiuation has getting worse and it brings all items and makes sense of slow query for large lists specially over threshold paths.

SharePoint Supports 30,000,000 Item per list But max item count should not be exceed 5000 in a folder including root folder of the list. DocumentSets are also considered as Folder. http://technet.microsoft.com/en-us/library/cc262787(v=office.15).aspx
http://technet.microsoft.com/en-us/library/ff603637(v=office.15).aspx

In that condition our suggestions , Don’t use “SPFolder.Item” property ! which is creating performance degradation.

Instead of that :

Use “SPQuery” if you want to get the item of a SPFolder (or DocumentSet)

 For Querying a DocumentSet item you can use following query;
SPList list = Site.RootWeb.Lists["Documents"];
// Or
// SPList = Site.RootWeb.GetList(“<List URL>”)


var query = new SPQuery();
query.RowLimit = 1;
//query.Folder = Library; //if it is present in a Folder.
query.ViewFields = "<FieldRef Name='ID' /><FieldRef Name='Title' />";//Limit the returning field count for gain performance.
query.ViewFieldsOnly = true;
 query.Query = string.Format(“<Where><And><Eq><FieldRef Name=’ContentType’ /><Value Type=’Computed’>Document Set</Value></Eq><Eq><FieldRef Name=’Title’ /><Value Type=’Text’>{0}</Value></Eq></And></Where>”, documentSetName);

var itemcollection = list.GetItems(query);

foreach(SPListItem item in itemcollection)
{
Console.WriteLine(item.ID + " " + item.Title);
}

Advertisement

A simple code impersonation in Sharepoint

Hello Everyone,

In this article i share with you a sample function that provide us code impersonation.For example you have login to sharepoint as system account and what to add an item to a custom list but you impersonate it by another user. As you know SPSecurity.RunWithElevatedPrivileges can provide us to run code as Sharepoint\system account.
So what if you impersonate with another user. The main key point is SPSite object constructor has parameter as SPUserToken, if you pass this token to the constructor,
it provide execute code with related user rights as defined with SPUserToken. For a real code impersonation you should better to use some native dll references (AdvApi32 DLL) . but this is also work for simple operations well.

Here the RunAsAdmin static class that contains ImpersonateRun fuction getting 2 parameters .
1) Account : the account to use rights
2) RunWithAdminDelegate : which is a delegate that provide us writing less codding for our implementations using lambda functions

Code Impersonation Sample
  1. public static class RunAsAdmin
  2. {
  3.     public delegate void RunWithAdminDelegate(SPSite site, SPWeb web);
  4.     public static void ImpersonateRun(string account,RunWithAdminDelegate myDelegate)
  5.     {
  6.         Guid webID = SPContext.Current.Web.ID;
  7.         Guid siteID = SPContext.Current.Site.ID;
  8.         SPUser privilegedAccount =null ;
  9.         if(string.IsNullOrEmpty(account))
  10.         {
  11.             privilegedAccount = SPContext.Current.Web.CurrentUser;
  12.         }
  13.         else
  14.         {
  15.             privilegedAccount = SPContext.Current.Web.EnsureUser(account);
  16.         }
  17.         SPUserToken privilegedToken = privilegedAccount.UserToken;
  18.         using (SPSite site = new SPSite(siteID, privilegedToken))
  19.         {
  20.             site.AllowUnsafeUpdates = true;
  21.             using (SPWeb web = site.OpenWeb(webID))
  22.             {
  23.                 //SPWebApplication webApp = web.Site.WebApplication;
  24.                 //  webApp.FormDigestSettings.Enabled = false;
  25.                 web.AllowUnsafeUpdates = true;
  26.                 myDelegate.Invoke(site, web);
  27.                 web.AllowUnsafeUpdates = false; ;
  28.                 //   webApp.FormDigestSettings.Enabled = true;
  29.             }
  30.         }
  31.     }
  32. }

the usage is very simple , Less coded less simple .

The usage
  1. protected void Page_Load(object sender, EventArgs e)
  2. {
  3.     RunAsAdmin.ImpersonateRun(“BLOG\\bpostaci”, (site, web) =>
  4.     {
  5.         SPList list = web.Lists[“MyList”];
  6.         foreach (SPListItem item in list.Items)
  7.         {
  8.             //Add Some items.
  9.         }
  10.     });
  11. }

see you next time.

Optional parameters for functions in c#

C# (before .net 4.0) does not support optional method arguments. However, there may be times when you are using components that were created in a language that supports optional arguments, such as legacy COM components or components created with Microsoft Visual Basic .NET.

class Example {    public void Test()     {        object missing = Type.Missing;       object urlblog = "http://blog.bugrapostaci.com";        VBTestService yourObject = new VBTestService();         // first parameter is url and other 3 are optional in definition of OptionalParameterFuction coded VB        yourObject.OptionalParameterFuction(ref urlblog, ref missing, ref missing, ref missing, ref missing);     } }

Happy Codding…

Ninject – Dependency Injector

Ninject is the ninja of dependency injectors.Ninject is a lightning-fast, ultra-lightweight dependency injector for .NET applications. It helps you split your application into a collection of loosely-coupled, highly-cohesive pieces, and then glue them back together in a flexible manner. By using Ninject to support your software’s architecture, your code will become easier to write, reuse, test, and modify.

Example of Code:

interface IWeapon
{
    void Hit(string target);
}
class Samurai
{
    private IWeapon _weapon;
 
    [Inject]
    public Samurai(IWeapon weapon)
    {
        _weapon = weapon;
    }
 
    public void Attack(string target)
    {
        _weapon.Hit(target);
    }
}
class WarriorModule : StandardModule {
  public override Load() {
    Bind<IWeapon>().To<Sword>();
    Bind<Samurai>().ToSelf();
  }
}
class Program
{
    public static void Main()
    {
        IKernel kernel = new StandardKernel(new WarriorModule());
        Samurai warrior = kernel.Get<Samurai>();
        warrior.Attack("the evildoers");
    }
}

..

My Rank is: 8.8

Project Home Page:
http://ninject.org/
Codeplex Home Page:
http://ninject.codeplex.com/
Download:for .NET Framework 2.0, 3.0, 3.5 version 1.0
http://ninject.org/assets/dist/Ninject-1.0-release-net-2.0.zip

You dont need to reinventing the wheel 🙂

c# Use As , not is in

In C#, use as, not is. The is keyword is used to see whether a reference can be cast as particular type, but it doesn’t return a reference converted to that type. So usually, if you get a positive result from the is, the first thing you’ll do is a cast—effectively implementing the same cast twice. With the as keyword, a reference cast as the new type is returned if it’s valid and a null is returned if it’s not. You then can check for the null and do what you like. The asapproach is fully 50% faster than the is approach.