Aswath’s Blog

Idea away with wings..

Archive for the ‘Sharepoint General’ Category

Reduce to bare bones of SharePoint debugging by creating the snagexecution toolbox

Posted by aswatharamadaka on April 21, 2009

Introduction

This series of Article is intended to help you getting ramped up with SharePoint programming. It’s about writing, troubleshooting and debugging SharePoint code. First you need to have prerequisite skills in .NET Development and in particular ASP.NET Development, you should also have basic understanding of SharePoint and how to use it from the User Interface , you must be able to create and deploy features and you should have some experience in working with content types and site columns.

Ready? Let’s get started!

The terms “Bug” and “Debugging” are facts of a programmer’s life. Debugging in general is a lengthy and tiresome task. In my mind, for you to be a good SharePoint developer, you must know how to troubleshoot your applications. The trick is SharePoint debugging can be quite complex for those who are new to the platform, that’s why I decided to kick off my series of article with how to simplify Debugging SharePoint code before we dive deep into the world of SharePoint programming. At the end of the article we’ll create the “SharePoint troubleshooting toolbox” that we’ll frequently use in our series “Getting Started to SharePoint Programming“.

Simplifying SharePoint Debugging By Creating The Troubleshooting Toolbox

Debugging in WSS or MOSS is similar to debugging an ASP.NET application but unfortunately debugging custom code in SharePoint isn’t as easy as just pressing F5 from inside Visual studio. While SharePoint provides an excellent platform for developing Web applications, debugging them can be a bit of a pain. In this article I will give you some debugging tips that could make your life easier and will help you deal with the silly “An unexpected error has occurred” screens. Also I will shed the light on some tools provided by the SharePoint community that facilitate the troubleshooting of SharePoint applications and error isolation and accordingly increasing your productivity.

Five main resources are available for you when you experience a problem:

1. Detailed Error Messages

2. Attaching the Visual Studio Debugger to W3WP.EXE

3. SharePoint Trace Logs

4. Windows Event Logs

5. Debug And Trace

1. Detailed Error Messages Vs. The Annoying Page!

Usually, an error message will be your first indication that something went wrong. Unfortunately, SharePoint uses a user friendly (Yellow & Blue) error page to show that a problem occurred. Yeah, they call it the user friendly page, but we, as developers, call it the Annoying Page. The first time I wrote SharePoint code, I received a screen like the one shown in the figure below:

 

 

 

spmag131

This error page points out that an assembly has thrown an unhandled System.Exception. Sometimes, the user-friendly error page will specify the nature of the error if the code that threw the exception used something more specific than System.Exception or if it included a message in the Exception class constructor.

We need to get a more detailed Error Message than the annoying “Unexpected error has occurred “. This can be achieved by doing three modifications to the Web.Config file from the virtual directory containing your SharePoint application. These modifications are listed in the in below table.

This error page points out that an assembly has thrown an unhandled System.Exception. Sometimes, the user-friendly error page will specify the nature of the error if the code that threw the exception used something more specific than System.Exception or if it included a message in the Exception class constructor.

We need to get a more detailed Error Message than the annoying “Unexpected error has occurred “. This can be achieved by doing three modifications to the Web.Config file from the virtual directory containing your SharePoint application. These modifications are listed in the in below table.

Tag Name Attribute Default Value Updated Value
customErrors mode On

<customErrors mode=” On” />

Off (or) Remote Only

<customErrors mode=” Off” />

SafeMode CallStack False

<SafeMode CallStack=”false” />

True

<SafeMode CallStack=”true” />

SafeMode AllowPageLevelTrace False

<SafeMode AllowPageLevelTrace=”false”

True

<SafeMode AllowPageLevelTrace=”false”

compilation debug False

<compilation batch=”false” debug=”false”>

True

<compilation batch=”false” debug=”true”>

No Custom Errors shows the full error to every client, every time. This is typically used Development environment, since there are no clients using it.

Remote-Only Custom Errors allow you to display custom errors only to remote clients. This means that if you are browsing your SharePoint site locally, you will get the fully detailed error messages. However, anybody else will receive the standard SharePoint page.

I recommend using the Debug Config feature to automate this process. This is just a feature that when you activate on a web application, it automatically tweaks the Web.Config of the specified web application across the farm.

2. Attaching the Visual Studio Debugger to W3WP.EXE

Now you have the standard ASP.NET error page with a stack trace , OK this is very helpful but you don’t want to guess what the problem might be and randomly change your code to fix it.

First thing you need to do to avoid the old fashioned trial and error technique is to enable debugging. This could be achieved by setting the compilation element debug attribute to true in Web.Config from the virtual directory containing your SharePoint application, otherwise, breakpoints inside Visual Studio will be shown but will never be used.

Once you’ve done that, there is one more thing you need to do in order to be able to debug your SharePoint code in Visual studio which is attaching a debugger to W3WP.EXE, Attaching a debugger in Visual Studio will allow you to step through the code and find exactly where the error occurs.

spmag22

spmag3

It’s really handy but there are three questions that I always receive from my colleagues when they get started to SharePoint programming, so I decided to share the answers with you.spmag10

The first one is: Sometimes, I set breakpoints and attach to the process but Visual Studio skips loading the symbols if I’m debugging a deployed assembly to the GAC and I fail to debug the code

Easy, Open Tools -> Options -> Debugging.

 

 

You’ll find an option labeled Enable Just My Code (Managed Only) as shown in the figure which is checked by default. Uncheck this option to be able to debug the assemblies located in the GAC. There is a common myth among .NET developers in general and especially SharePoint ones, that in order to debug assemblies that have been deployed to the GAC, you need to copy the debug symbols (PDB File) to the GAC as well. This was true in the early days of .NET but this is no longer true.

The second one is: When I try to attach the debugger to the W3WP.exe process to debug, I always see multiple instances of it. Which one should I attach to?

Ok, this is easy too. Just follow the following steps.

  • Open the command prompt window, run IISAPP to get a list of the current instances of W3WP.exe.

spmag_cmd

  • Note the PID of the instance that corresponds to your web application.
  • Now return to VS, select Debug -> Attach to process and attach to the W3wp.exe instance with an ID equivalent to the PID you got in step 2 -> click Attach.
  • Now you can trace through the code and find the error causes easily.

But the question still remains, why sometimes are they more than one w3wp.exe instance? This is because the SharePoint Administration Site Collection and the SSP Administration site always have their own Application pools for error isolation purposes.

And the third question is : Is it possible to debug Inline code blocks ?

Actually, I hate Inline Code Blocks and it’s really a good practice to avoid it due to the performance issues when the JIT compiler compiles them but YES, you can do that.

So now you knew the process of debugging? Very boring and repetitive huh? Hmm, Can’t that be automated?
Fortunately Jonathan Dibble, a brilliant developer, created a very handy “Debugger Feature” that can be installed and activated on a SharePoint site to automate this process. Once activated, the Debugger Feature adds an “Attach Debugger” menu item to the Site Actions menu. Extremely helpful and faster than doing that from visual studio.

spmag6

3 .Unified Logging Services (SharePoint Trace Logs)

Sometimes you receive error screens while activating a feature or creating a Site Collection or during deploying packages. For instance, a couple of months ago I got an annoying error “File not found” when creating a site collection from a custom template!

SharePoint trace logs are at your disposal when you need to troubleshoot errors occurring before and after custom code; they are very useful in the deployment and provisioning operations as they are the main sources of information about everything happening inside SharePoint.

Most of SharePoint components use the Unified Logging Services (ULS), those logs are normal text files and you can find them in the 12 hive at 12\Logs. You can tweak the ULS settings via the Diagnostic logging link under Logging and Reporting in the operations section of SharePoint central administration to control the verbosity of events captured in the Log files, you can modify the settings per category or for all the categories as shown in the figure; thus modifying the number of events captured. The list entries are sorted in order from most-critical to least-critical. I always just set all of the categories to verbose because it’s sometimes difficult to specify the categories needed to be changed when a problem occurs.

spmag7

If you want to tweak the verbosity setting per category, make sure to leave the default value of the General category for trace logging as it is (Verbose) because entries about the provisioning and deployment processes are logged under the General category. Also be aware that updating all categories will make you lose the changes you made to individual ones.

When you choose to increase the number of events captured by the ULS, you will find the log files very cluttered and hard to use, and SharePoint provides no built-in viewer. To fill the gap and facilitate troubleshooting, free third-party tools exist like LogViewer, SPTraceView and WSS/MOSS Log File Reader .Some utilities including SPTraceView will aggregate log data from more than one server in the farm.

Below figure shows LogViewer in action.

I’d also like to point out that you can write code that incorporates logging to MOSS logs. Writing to the same trace log alleviates the need for developers to log their development information in other places such as the Windows Event Log, which is more commonly used by system administrators.

spmag8

try{

      //  SPSite site =SPContext.Current.Site;

 

    }

        catch(Exception ex){

        Microsoft.Office.Server.Diagnostics.PortalLog.LogString(“Exception Happened : {0} –> {1}”,ex.Message,ex.StackTrace);

        //throw new SPException(“Unknown Error Occured. Please Contact the administrator

    }

 

The only limitation to using the code snippet above is that you cannot set the log event level (e.g. low, medium, and critical) as it’ll always display the error level in the trace logs as High. The logger is located in 12\ISAPI \Microsoft.Office.Server.dll and therefore it’s only available with the MOSS install, not WSS 3.0.

What if you need to write into SharePoint trace logs while having full control on the error level? This is a pretty easy thing to do, because MSDN has a wonderful sample of code that you can reuse. I always use this code in my features.

Simply add the class to your project and then you can write to the logs using something like the following code.

TraceProvider.RegisterTraceProvider();
TraceProvider.WriteTrace(TraceProvider.TagFromString(”XXXX (must be 4 letter tag)”), TraceProvider.StringToSeverity(”Exception or Information”), Guid.NewGuid(), “Method Name”, “Assembly Name”, “Project Name”, “Message”);
TraceProvider.UnregisterTraceProvider();

4 . Windows Event Logs

You should include Windows Event Logs as part of your normal troubleshooting because it sometimes contains useful entries that SharePoint is unable to log via ULS. You can increase and decrease logging by severity level in the same way you do for ULS.

It’s possible to log errors to the system event log from your custom code but you need to promote the privileges as shown.

    try{

      //  SPSite site =SPContext.Current.Site;

 

    }

        catch(Exception ex){

        SPSecurity.RunWithElevatedPriviliges(

        delegate{

        System.Diagnostics.EventLog.WriteEntry

            (“Your Webpart/Feature Name”,

            “Exception in yourfunction(): “+ex.Message+

            “Stack Trace :”+ex.StackTrace,

            ,EventLogEntryType.Error);

 

    }

        );

       // Microsoft.Office.Server.Diagnostics.PortalLog.LogString(“Exception Happened : {0} –> {1}”,ex.Message,ex.StackTrace);

        //throw new SPException(“Unknown Error Occured. Please Contact the administrator

    }

 

5. Debug and Trace

After you take your SharePoint site live, you are not the only one who is using it anymore (hopefully), so you need effective plans to track down errors.

System.Diagnostics.Debug and Trace statements are very useful in this case. Used in conjunction with DebugView you can determine what has gone wrong! Debug Calls are removed from the release builds, so you should use them in your development environment but Trace Calls remain in release code and so will add an overhead to the code execution yet they are very helpful when you cannot attach a debugger (for instance on the staging or the production environments) . Since manually adding trace calls might be time consuming, I would strongly recommend using a tool such as ReSharper to drop in these statements quickly rather than relying on typing or copy/paste. The next figure shows the trace output usingDebugView.

spmag9

SharePoint SnagExecution Toolbox!

Well, let’s create our debugging toolbox, the following utilities should be included in our SharePoint debugging toolbox; we’ll certainly need them in our long journey with SharePoint development.

Summary

This article hat will help you getting started with SharePoint programming and troubleshooting utilities and tools that can really make your life easier before getting our hands dirty with SharePoint code since troubleshooting can really be a nightmare for those who are new to the platform.

Posted in Sharepoint General | Leave a Comment »

About Feature Elements

Posted by aswatharamadaka on April 18, 2009

Feature is one of the roubust way to eliminate complexity,versioning, inconsistency.

Feature Snippet:

<Feature

Id=”ud34C3075-X5C0-CD#6-9XCF-CA6BBC7D43″

ActivateOnDefault = “TRUE” | “FALSE”

Title=”Location Services”

Description=”……”

Scope=”Web/Site/WebApplication/Farm“>

<ActivationDependencies>

<ActivationDependency

FeatureId=”al94C3075-X5C0-CD#6-9XCF-4T6BBC7DA5″ />

</ActivationDependencies>

<ElementManifests>

<ElementManifest

Location=”Location\LocationPart.xml”/>

<ElementManifest

Location=”CustomerLocation\CustomerLocationList.xml”/>

<ElementFile

Location=”test.aspx”/>

</ElementManifests>

</Feature>

ActivateOnDefault

Optional Boolean. TRUE if the Feature is activated by default during installation or when a Web application is created; FALSE if the Feature is not activated. This attribute equals TRUE by default. The ActivateOnDefault attribute does not apply to site collection (Site) or Web site (Web) scoped Features.


In general, Farm-scoped Features become activated during installation, and when a new Web application is created, all installed Web application-scoped Features in it become activated.


Scope :

Feature one can set scope at the individual Web site level.

A site collection Feature contains items that apply to the site collection

as a whole (e.g.,content types that are shared across the site collection),

as well as items that can be activated per site.


Site Collection or Site scope include list definitions

(templates and instances), modules (file sets), and item content type behaviors

(per-item custom menu options and per-item events).


Web (Web site scope)


Control,Custom Action,Custom Action Group,Hide Custom Action,List Instance, List Template,Module,Receiver


Site (site collection)


Content Type,Content Type Binding,Control,Custom Action

Custom Action Group,Feature/Site Template Association,Field

Hide Custom Action,List Instance,Module,Workflow


WebApplication (Web application)


Control,Custom Action,Custom Action Group,Document Converter

Feature/Site Template Association,Hide Custom Action


Farm (farm)


Control,Custom Action,Custom Action Group,Feature/Site Template Association,Hide Custom Action


ActivationDependency

Features can have dependencies on other Features, and these other Features can be activated when the Feature that depends on them is activated.


Note : Windows SharePoint Services does not support a cross-scope activation dependency if the current Feature depends upon another Feature at a more restrictive scope, or if the current Feature depends on a hidden Feature. Click here


ElementManifest : Definition for a feature element


ElementFile : Support file required for the Feature this may contain


master pages, page layouts, images, style sheets etc


Click here


Feature that provisions the instances does not remove the instances upon deactivation.


Provision a File : the Module element within a Feature or site definition. The Module element allows you to add one or more files, or file set, to a SharePoint Web site or document library.


Type=”GhostableInLibrary”


This setting tells Windows SharePoint Services to create a list item to go with your file when it is added to the library


Type=”Ghostable”


Provisioning a file outside a document library.

Posted in Sharepoint General | Leave a Comment »

Sharepoint Designer is now free!

Posted by aswatharamadaka on April 14, 2009

Late to this game, as usual but still adding here.

Today I am excited to share with you some news about SharePoint Designer 2007. Starting now (April 2, 2009), SharePoint Designer 2007 will be available as a free download! microsoft want more of you customizing SharePoint and feel that this a good way to put the tool in the hands of more people. You can find a lot more information in microsoft site including:

a) Letter to our Customers

b) Frequently Asked Questions

c) Free Download

Also, make sure to watch this YouTube video where Tom Rizzo and J.R. Arredondo discuss these changes and provide some insights into what is coming in the future. Or if you prefer to download the video, just pick the appropriate version for your bandwidth in the list below:

· Small size video (6MB)

· Medium size video (17 MB)

· Large size video (83 MB)

 

I’ve been using SD for customizing our internal site we use to run our processes, it is invaluable tool

great to go head and start use it….

 

Posted in Sharepoint General | Leave a Comment »

Why do SharePoint implementations fail?

Posted by aswatharamadaka on March 25, 2009

The term failure is a harsh word. Regardless of how you may view the term in your personal or professional life, in SharePoint terms, I equate the word failure to any SharePoint implementation that does not meet its full potential within an organization.  For those of you who know me, you know that I have very high standards for both myself, and my work.  When I think about SharePoint Implementations over the past 5 years, the word failure jumps to the forefront of my mind.  This action occurs because it is only on the rare occasion, that I see an implementation of SharePoint meet its true potential within an organization.      

I believe that most SharePoint implementations fail (…to meet their true potential) due to a series of similar pitfalls. From my real-world experience, some of the most common causes for a failed SharePoint implementation orbit around the following:

§ Inadequate resources to support the implementation
§ A lack of planning
§ Improper expectations as to SharePoint’s role within the organization

I am not one to simply point out a problem without also providing supporting details around a solution. This blog doesn’t simply complain about a problem.  It offers a solution as well. J  Through a series of blog posts on the topic of why SharePoint implementations fail (… to meet their true potential), I’ll be explaining common pitfalls, discussing real-world history, and explain the impacts these pitfalls can have within an organization’s SharePoint implementation. 

From here on out, I’ll try to explain things from the perspectives of both the SharePoint Administrator, as well as a business owner.  Finally, I’ll provide possible avenues for improving upon these pitfalls and provide guidance as to how these problems can be avoided in the future.

Stay tuned!

Posted in Sharepoint General | Leave a Comment »

SPApplication Pool Hidden hoods

Posted by aswatharamadaka on March 25, 2009

As always, I was wandering through the OM of our beloved SharePoint searching for getting to the Application Pools of a WebApplication. The case is that for our beloved LCM tool I was trying to get all the application pool accounts and add those to the LCM web as contributors.

Since I came across an issue regarding the fact that when a site or a web is deleted and you’ve checked ‘Log the deletions in SharePoint’ in the configuration page. The application pool accounts couldn’t get access to the “Deleted Sites” list on the LCM Web. (btw this is still an issue and is not solved by adding the accounts to the Web. This is due to the fact that the service accounts must be added as a farm admin to the Central Admin.. and we don’t want that either ;) .

But to come back to the topic.. I’ve found an interesting class and that is the SPApplicationPool class. And.. well.. I was shocked to find out that there is a property called “Password”. Well actually I wasn’t shocked to found out that the property existed.. but I was shocked to find out that the property was not only settable but also gettable!!

So when running the following piece of code..

SPWebApplicationCollection webApplicationCollection = SPWebService.ContentService.WebApplications;
foreach(SPWebApplication webApplication in webApplicationCollection)
{            
    SPApplicationPool applicationPool = webApplication.ApplicationPool;
    Console.WriteLine("WebApplication "+ webApplication.Name);
    Console.WriteLine("Username "+ applicationPool.Username);
    Console.WriteLine("Password "+ applicationPool.Password);
}

..it will give you the passwords of each application pool account. Though I must say that this of course will only run if you logged in as a farm admin since this comes out of the Share Point.Administration name space. But I must say that this is quite tricky..  especially when there is another property in there called “SecurePassword”.

Please let me know your thoughts ;)

Posted in Sharepoint General | Leave a Comment »

SharePoint caching and CacheDependency

Posted by aswatharamadaka on December 21, 2008

One of the things that can really help the performance of your site is caching. Going to the SharePoint database for every request to retrieve a file can be very expensive, particularly if once the file has been retrieved you need to process it further. Its a good idea to cache that file (or the processed results), using the standard System.Web.Caching.Cache.

HttpContext.Cache

The HttpContext.Cache property gives you easy access to the current cached objects. The collection of cached objects are stored using a string as a key and generally you would add your file using code similar to the following…

HttpContext.Current.Cache.Add(“YourKey”,

                              oYourSharePointFile,

                              null,

                              DateTime.Now.AddMinutes(2),

                              System.Web.Caching.Cache.NoSlidingExpiration,

                              System.Web.Caching.CacheItemPriority.Normal, null);

Once added you can access your cached object using…

string sFileContents = (string)HttpContext.Current.Cache["YourKey"];

This saves you having to go to SharePoint again to retrieve the file contents for every request. The problem is that you will have to load it again in two minutes, and if the file changes within that two minutes they will not be reflected. Also if the file hasn’t changed you are re-loading it even though you don’t need to.

System.Web.Caching.CacheDependency

This is where the CacheDependency class helps you out as it allows you to invalidate the cache only when the file changes. This allows you to change the code to the following…

HttpContext.Current.Cache.Add(“YourKey”,

                              oYourSharePointFile,

                              new SPFileCacheDependency(SPContext.Current.Site.Url, XslFullPath),

                              System.Web.Caching.Cache.NoAbsoluteExpiration,

                              System.Web.Caching.Cache.NoSlidingExpiration,

                              System.Web.Caching.CacheItemPriority.Normal, null);

Now the cached SharePoint file will only be removed when it is invalidated by the CacheDependency, not after a set period of time, the only problem being that SharePoint does not provide an implementation of this class for you to use.

In .Net you not only have the CacheDependency, which allows you to monitor files, but also the SqlCacheDependency, which allows you to check for database changes. Unfortunately neither of these classes help us with SharePoint files and so we need to provide our own implementation.

Writing your own SPFileCacheDependency class

In order to provide our own version we need to write a class which inherits from CacheDependency

public class SPFileCacheDependency : CacheDependency

{

    private string _uniqueID = Guid.NewGuid().ToString();

    private string _siteUrl;

    private string _itemUrl;

 

    public void RaiseChangedEvent(object sender, SPFileCacheEventArgs e)

    {

        base.NotifyDependencyChanged(sender, e);

    }

 

    public SPFileCacheDependency(string siteUrl, string fileUrl)

    {

        _itemUrl = fileUrl.ToLower();

        _siteUrl = siteUrl.ToLower();

        SPFileWatcher.Current(siteUrl).AddDepedentItem(this, fileUrl);

    }

 

    public override string GetUniqueID()

    {

        return _uniqueID;

    }

 

    protected override void DependencyDispose()

    {

        try

        {

            SPFileWatcher.Current(_siteUrl).RemoveDepedentItem(this, _itemUrl);

 

            base.DependencyDispose();

        }

        catch (Exception ex)

        {

            Log.Trace(ex);

        }

    }

}

This class overrides the important methods in order to manage the dependency, it uses another class (SPFileWatcher) to actually manage the process of checking the files. This class uses a timer to periodically check the files to see if they have changed. The implementation of SPFileWatcher is below…

public class SPFileWatcher

{

    class ItemDetails

    {

        public DateTime LastModified;

        public List<SPFileCacheDependency> Dependencies = new List<SPFileCacheDependency>();

    }

 

    private static SPFileWatcher _current;

    private string _siteUrl;

 

    private Timer _timer;

    private Dictionary<string, ItemDetails> _items;

 

    public SPFileWatcher(string siteUrl)

    {

        _items = new Dictionary<string, ItemDetails>();

        _siteUrl = siteUrl.ToLower();

    }

 

    private Dictionary<string, ItemDetails> Items

    {

        get { return _items; }

        set { _items = value; }

    }

 

    public static SPFileWatcher Current(string siteUrl)

    {

        if (_current == null)

            _current = new SPFileWatcher(siteUrl);

 

        return _current;

    }

 

    public void AddDepedentItem(SPFileCacheDependency owner, string urlOfItem)

    {

        try

        {

            if (!Items.ContainsKey(urlOfItem.ToLower()))

            {

                ItemDetails details = new ItemDetails();

                details.LastModified = DateTime.UtcNow;

                details.Dependencies.Add(owner);

                Items.Add(urlOfItem.ToLower(), details);

            }

            else

            {

                ItemDetails details = Items[urlOfItem.ToLower()];

                details.Dependencies.Add(owner);

            }

 

            EnsureStarted();

        }

        catch (Exception ex)

        {

            System.Diagnostics.Trace.WriteLine(ex);

        }

    }

 

    public void RemoveDepedentItem(SPFileCacheDependency owner, string urlOfItem)

    {

        if (!Items.ContainsKey(urlOfItem)) return;

 

        ItemDetails details = Items[urlOfItem];

        if (details.Dependencies.Contains(owner)) details.Dependencies.Remove(owner);

 

        if (details.Dependencies.Count == 0) Items.Remove(urlOfItem.ToLower());

 

        if (Items.Count == 0)

        {

            _timer.Stop();

            _timer.Dispose();

            _timer = null;

        }

    }

 

    protected void EnsureStarted()

    {

        if (_timer == null)

        {

            _timer = new Timer(10000);

            _timer.AutoReset = true;

            _timer.Elapsed += new ElapsedEventHandler(Timer_Elapsed);

            _timer.Start();

        }

    }

 

    void Timer_Elapsed(object sender, ElapsedEventArgs e)

    {

        SPSite oSite = null;

        try

        {

            oSite = new SPSite(_siteUrl);

 

            string[] arKeys = new string[Items.Keys.Count];

            Items.Keys.CopyTo(arKeys, 0);

 

            for (int c = Items.Count – 1; c >= 0; c–)

            {

                string sKey = arKeys[c];

                try

                {

                    SPFile oFile = oSite.RootWeb.GetFile(sKey);

                    ItemDetails details = Items[sKey];

 

                    if (details.LastModified < oFile.TimeLastModified)

                    {

                        System.Diagnostics.Debug.WriteLine(“Raising dependency changed: “ + sKey);

                        SPFileCacheDependency[] copy = new SPFileCacheDependency[details.Dependencies.Count];

                        details.Dependencies.CopyTo(copy);

                        foreach (SPFileCacheDependency d in copy)

                            d.RaiseChangedEvent(this, new SPFileCacheEventArgs());

                    }

                }

                catch (Exception ex)

                {

                    System.Diagnostics.Trace.WriteLine(ex);

                }

            }

        }

        catch (Exception ex)

        {

            System.Diagnostics.Trace.WriteLine(ex);

        }

        finally

        {

           oSite.Dispose();

        }

    }

}

public class SPFileCacheEventArgs : EventArgs

{

}

This class does all the work of periodically checking the cached files and invalidating them when they have changed. This implementation currently checks every 10 seconds, this can be changed to suit your own needs.

Now you should be able to cache your SharePoint files and only have to return to SharePoint when the file has actually changed. Personally I use a lot of XSLT and using this technique saves re-loading the XSL which leads to having to re-compile the transform. I cache the compiled XSL object and put a dependency on the XSL file.

You can use this class to monitor any files or even extend it to monitor a list item, a folder or a SharePoint document library.

Posted in Sharepoint General | Leave a Comment »

New: SharePoint Essentials for .NET Developers

Posted by aswatharamadaka on December 15, 2008

If you are a .NET developer curious about what is SharePoint and want to get started with SharePoint development, you should check out The SharePoint Developer Introduction for .NET Developers resource set announced today at Tech Ed. This is a new set of webcasts, virtual labs, screencasts, presentations, demos, white papers, hands on labs, and resources that show you how to build enterprise solutions using different SharePoint components such as:

  • Web Parts
  • Data Lists
  • Event Handlers
  • Workflow
  • Silverlight
  • Page Navigation
  • Page Branding
  • Web Services
  • Custom Content Types
  • User Management

You should take a look at the The SharePoint Developer Introduction for .NET Developers Web site to find pointers to learning resources for all of the components listed previously. You should also check out Paul Andrew’s blog post about the new set ofSharePoint Developer Webcasts that provide introductory SharePoint developer topics for .NET developers.

Also, if you want to learn more about the big picture, see a roadmap, and get an overview of SharePoint Products and Technologies, you should read Introduction to SharePoint Products and Technologies for the Professional .NET Developer. This  is an MSDN article that explores the extensible solution platform of SharePoint Products and Technologies and opportunities for its use in .NET development. It shows how developers experienced with the .NET Framework can take advantage of the built-in features and capabilities offered by SharePoint Products and Technologies to expand their existing knowledge, and build enterprise-scale Web-based solutions to reach the growing SharePoint audience.

Paul wrote this article together hoping it could help you to learn more and get started with SharePoint development. We hope you enjoy this paper and all the different SharePoint for .NET developers learning resources announced today.

Posted in Sharepoint General | Leave a Comment »