Automatically Refresh A SharePoint 2010 Calendar View

For some reason (at least to my knowledge) SharePoint 2010 does not provide a function to automatically refresh a SharePoint calendar view’s items at a given interval. The lack of this feature means a full page refresh is required any time a user wishes to check for any updates. While this might be suitable for infrequently updated calendars, for calendars that get frequently updated this is not desirable.

Fortunately, SharePoint does include a JavaScript library that provides methods for updating calendar views asynchronously. The particular library of interest is:

SP.UI.ApplicationPages.CalendarInstanceRepository

This repository contains a pointer to all of the calendar instances on the current page. If there is only one instance on the page, or you’re only interested in the first instance, there is a helper method firstInstance() to retrieve that calendar. Otherwise, you can find the collection of calendars as properties on the $o_0 property. You can turn this into a list using the following code:

var calendars = [];
var d = SP.UI.ApplicationPages.CalendarInstanceRepository.$o_0;

for (var k in d) {
  calendars.push(d[k]);
}

Using The Calendar Repositories

Now that we have access to the calendar(s) we need to use them. One way of doing this is to create a hidden content editor web part that uses the following script to call refreshItems() every 10 seconds. First, create a new file RefreshCalendar.html and publish it somewhere on your SharePoint site.

<script type="text/javascript">
  setInterval(function() {
    try {
      var calendar = SP.UI.ApplicationPages.CalendarInstanceRepository.firstInstance(); // Get the first calendar instance on the page
      if (calendar) {
        calendar.refreshItems(); // async refresh of calendar items
      }
    }
    catch (e) {
      // ignore
    }
  }, 10000); // Every 10 seconds
</script>

Next, add a content editor web part to the same page as the calendar view you wish to update automatically; setting the content link to the location of the RefreshCalendar.html page, and setting the Chrome Type to none to remove any headers, borders, e.t.c. (i.e. make the content editor web part invisible to the user).

Automatically Refresh a Sharepoint Calendar View Content Editor

Now, when a user goes to the calendar view, the items are automatically updated every 10 seconds. Because the call is asynchronous the user will not be impacted when an update occurs, even if they are adding, or editing, a calendar item.

Getting a Hierarchy of Outlook Folders With Their Entry ID

Simple console application to output a hierarchy of Outlook folders, with their Entry ID, using NetOffice.

using System;

namespace OutlookFolderIdGrabber
{
    public class Program
    {
        public static void Main(string[] args)
        {
            using (var application = new NetOffice.OutlookApi.Application())
            {
                DisplayFolder(application.Session.DefaultStore.GetRootFolder());
            }
        }

        private static void DisplayFolder(NetOffice.OutlookApi.MAPIFolder folder, int level = 0)
        {
            Console.WriteLine($"{new string(' ', level)}{folder.Name} : {folder.EntryID}");

            foreach (NetOffice.OutlookApi.MAPIFolder childFolder in folder.Folders)
            {
                DisplayFolder(childFolder, level + 1);
            }
        }
    }
}
<?xml version="1.0" encoding="utf-8"?>
<packages>
  <package id="NetOffice.Core" version="1.7.3.0" targetFramework="net461" />
  <package id="NetOffice.Outlook" version="1.7.3.0" targetFramework="net461" />
</packages>

TRIM Outlook Add-In Module Not Found

Another HP TRIM Outlook issue; this time when trying to check-in a mail item from Outlook, when the TRIM record type has an External Link associated with it – in this case a Generic AddIn (.NET). When the Outlook Add-In gets to the point that it is checking the file in to TRIM the error The specified module could not be found. (Exception from HRESULT: 0x8007007E) is thrown, but only if there is an AddIn associated with the record type of the record being created, otherwise it works fine.

As with most error messages, this one is not very helpful, simply indicating that a module could not be found. Fortunately this was working on my local workstation, however, the issue was present for test users on their thin client environment, so it was just a matter of finding out what was different between the two environments. After some investigating, I remembered that I had manually added the TRIM client installation directory to the PATH system variable to enable running a web site which uses the HP TRIM SDK. Removing the installation dir from the PATH variable did indeed result in the same error message, and funny enough adding the dir back resolved the issue, on both my local instance and on the thin client instance. I don’t know why the TRIM client install doesn’t just add the TRIM directory to the PATH variable by default. Oversight by HP? I’m sure it used to be… there are also plenty of SDK related forum posts suggesting to add it when starting your application (that doesn’t really help in this instance).

To add the TRIM installation directory to your PATH system variable go to your system settings; (start » type “Edit the system environment variables”) or (start » right-click Computer » Properties » Advanced system settings) » Environment Variables » under System variables locate and select Path » click Edit » append your TRIM install folder (default TRIM installation directory should be either; C:/Program Files/Hewlett Packard/HP TRIM or; C:/Program Files (x86)/Hewlett Packard/HP TRIM depending on your installation preference.

TRIM Microsoft Word Add-In HP TRIM SDK Not Found

If you’re using the Microsoft Word integration feature with HP TRIM and receive the error message “Could not load file or assembly ‘HP.HPTRIM.SDK’ or one of its dependencies. The system cannot find the file specified.” chances are you probably have a generic .NET Add-In registered in your TRIM dataset for the record type you’re trying to save your Word document as.

To solve the issue you can copy the HP.HPTRIM.SDK.dll from your Trim installation folder into your Microsoft Office executable folder (e.g. C:/Program Files (x86)/Microsoft Office/Office14 or C:/Program Files/Microsoft Office/Office14 *note your office version may vary e.g. Office11, Office15, etc).

There may be another way to resolve this issue, but so far it’s the easiest and only fix I have worked out.

TRIM Outlook Add-In COM Exception

Recently I was getting the error 0x80030002 STG_E_FILENOTFOUND while trying to run any TRIM 7.3 Outlook Add-In function. The Outlook Add-In had loaded fine and was bringing up all the available TRIM options, it was just when I tried to execute one of the options that it would throw the, oh so very “helpful”, error message as with most COM operations. It wasn’t until I found this thread over in the HP forums that I discovered that Cisco Unified Personal Communicator can interfere with the TRIM Add-In. According to another post, any ODMA integration can cause issues with HP TRIM’s Outlook Add-In, in their case, it was Novell GroupWise causing the issue.

Trim Outlook Com Exception
Unable to cast COM object of type ‘System._ComObject’ to interface type ‘Redemption.SafeMail’. This operation failed because the QueryInterface call on the COM component for the interface with IID ‘{0A95BE2D-1543-46BE-AD6D-18653034BF87}’ failed due to the following error: could not be found. (Exception from HRESULT: 0x80030002 (STG_E_FILENOTFOUND)).

Fortunately for me, Cisco Unified Personal Communicator was no longer required to be installed (and has been replaced by Jabbr – although I did not test if Jabbr causes issues with TRIM’s Add-In), so to resolve the issue I just had to uninstall Cisco Unified Personal Communicator; for good measure I also did a repair of HP TRIM Microsoft runtimes for VS 2008 and a repair of HP TRIM.

Impersonating Any User On SharePoint

When a SharePoint web part, or similar custom code, is running on SharePoint the active SPContext will either be impersonating the current user’s account or the guest account (if enabled). This means that all of SharePoint’s security is maintained when accessing lists, items, etc. However; there may be some instances when you want the custom code to be able to access items (or lists, etc.) which the current user does not have access to without actually giving the user direct access to these particular items. Fortunately, this is a pretty easy task to achieve and can be accomplished in a number of ways.

Method 1. Using elevated security

This method takes advantage of the Microsoft.SharePoint.SPSecurity static helper methods, in particular, the RunWithElevatedPrivileges method. The objective of this method is to execute code with full control regardless of the users delegated roles. Example:

SPSecurity.RunWithElevatedPrivileges(() => {
    // Code running with full control
});

The most important thing to note here is that any SharePoint context objects that have already been instantiated outside of the elevated security blocks do not have full control, even if referenced from within the elevated security blocks. This means that you can not simply call SPSecurity.RunWithElevatedPrivileges(() => SPContext.Current.ListItem.Delete()); and expect it to work if the current user does not have permission to the delete the current list item; instead, you must instantiate a new SPSite object within the elevated security blocks and then delete the list item. For example:

SPSecurity.RunWithElevatedPrivileges(() =>
{
    using (SPSite site = new SPSite(SPContext.Current.Site.ID))
    {
        using (SPWeb web = site.OpenWeb(SPContext.Current.Web.ID))
        {
            SPList list = web.Lists[SPContext.Current.List.ID];
            SPListItem item = list.Items[SPContext.Current.ListItem.UniqueId];
 
            item.Delete();
        }
    }
});

Now when the above code runs, it should not have any problems deleting the current list item, even if the current user does not have permission to delete the item.

Method 2. Impersonating another user

This is another simple method which involves instantiating a new SPSite object running under a different context to that of the invoking users’ context. To achieve this, when we are instantiating the new SPSite object, we simply pass in the SPUserToken of the user we wish to impersonate. For example, we could run under the system account:

using (SPSite site = new SPSite(SPContext.Current.Site.ID, SPContext.Current.Site.SystemAccount.UserToken))
{
    // code here
}

The thing to note with this method is that the user being impersonated needs to have permission to perform the actions specified.

The UserToken is available from SPUser objects. So before creating the new SPSite object, you would need to find the user object for the user you wish to impersonate, or otherwise, have some way of reference the user’s token.

Unable To Instantiate TRIM Database: 80040154

I recently came across this error while attempting to connect to TRIM 6 R2 via the TRIMSDKRetrieving the COM class factory for component with CLSID {8A354548-6BCB-11D3-B273-00A0C9FC3DC0} failed due to the following error: 80040154.

This was a little alarming because it was using the same data adapter as a few other TRIM projects, which were working fine; the only difference between the project was that this particular project was a WPF application, and all of the other applications were ASP.NET applications. This particular application had also previously worked fine, the only change was that I had been upgraded to a 64-bit environment.

After a bit of playing around and research, I discovered the TRIM SDK will not connect under a 64-bit process.

Workaround

  1. In Visual Studio, right-click your project and go to Properties (last item).
  2. Select the Build tab.
  3. Change the Configuration option to All Configurations.
  4. Change the Platform Target to x86.

This will ensure that your application will only run under an x86 architecture, and will be able to connect to TRIM even on a 64-bit host.

Looking at the QuickSpecs for TRIM 7 it is being based on a 64-bit architecture and therefore this issue should be eliminated come TRIM 7 (in addition to some SDK enhancements and UI integration tools).

Oracle 06413: Connection Not Open (x64)

Having changed to a 64-bit development machine at work recently I ran into an Oracle error while trying to generate files using CodeSmith. This error was ORA-06413: Connection Not Open. Assuming it was a connection string error, as I had not run this particular generation in some time and it was likely that the server or username/password had changed, I proceeded to test the connection from SQL Developer. Success!

After ruling out that the connection was indeed valid I did a quick Google search for the error message. After a few clicks I discovered a very well known (has been around for a few years) Oracle issue; When executing an Oracle command from an application with parentheses or equals — ‘(‘ or ’)’ or ‘=’ — in the path than the specified error message is thrown.

In this particular case, CodeSmith had been installed under C:/Program Files (x86)/CodeSmith which was causing Oracle to fail. The quickest workaround was to simply move CodeSmith from the Program Files (x86) path e.g. into C:/CodeSmith. However; there is a patch (5383042) for Oracle 10g, which is also applied to Oracle 11G.

See Code, See CodeRun

Merbla wrote a short post today about a site he came across, CodeRun. The site is an online code repository, with the added advantage of an online IDE include on the site which allows you to see the code and run/debug it as it is. After signing up for a free account you can create your own projects (AJAX, ASP.NET, PHP and WPF — AJAX and ASP.NET also have support for Facebook applications) which you can develop, store and run all from their website.

The concept is brilliant — everything from start to go can be done online via your standard web browser (currently only supports Internet Explorer and FireFox) and publishing of your source code is as simple as a right-click and a left-click. Once the source has been published other people can freely go and search for source code in the repository and open it directly in the browser, make modifications and run them all from within the browser.

However; The actual implementation of it so far (while still very impressive) is significantly lacking from a development perspective. Although it is possible to do the majority of thing you can do in Visual Studio, it is a little cumbersome and slow at times and does have a few limitations. For example, there is no toolbar — and therefore no drag and dropping of controls (which Microsoft presentations always seem to contain a lot of ;-).

Although the site seems to be focused on web applications some features are also available in the online IDE. You do not have the ability to create folders with underscores in them, and there does not seem to be any way of creating the special ASP.NET folders such as App_Data or App_Themes… not such a big deal. Designer files are not automatically created and if you try to create one an exception is thrown saying the file already exists.

The biggest problem, however, is the speed. Perhaps it is just my machine or my internet connection, but the online IDE is very slow to use and navigate. Menus and prompts tend to hang the browser for a couple of seconds before they load and the IntelliSense (ctrl+space) does not allow function correctly. Code highlighting, although not important or required, is lacking from the Visual Studio equivalent and take a significant amount of time to process and display.

Copying and pasting from Visual Studio into the online IDE also seems to be out of the question, as it seems to paste the text multiple times; Copy and paste from within the online IDE works fine.

All that being said the online IDE quite features rich and imitates Visual Studio very well. You are able to apply breakpoints and step through code, attach to processes (only online applications — not system processes), watch variables, etc. There is also an option to open a project from a zip file — which works great, providing you zip the project from the root of the project folder (it must not be in a sub folder).

In the end (as Merbla suggested in his post) something like this teamed up with StackOverflow, for the purpose of displaying simple solutions to problems with working example would be brilliant! However, as far as online development goes I think there is a long way to go.

See running example: Hello World!

InfoPath Roles And Views

One useful feature of InfoPath is its built in support for user Roles. While it is not an overly powerful (and it should not be used for security purposes as all data can be viewed and edited in XML format via notepad or a similar) it can be handy for automatically switching views based on AD users or groups.

To add a role simply go to Tools -> User Roles (alt + t + e) and click Add (alt + a). You can then specify which users, groups or user names from the form should belong to the new role.

One thing to note is that when you are designing an InfoPath form and click “Preview Form” it shows the form based on the default role. If you wish to preview the form under a different role you need to go to File -> Preview Form -> With User Role… (alt + f + r + r). The form will then be launched in preview mode under the select role.

There is also the option to set a role as either the default role or the initiator role (only one role can occupy either or both of these options). The default setting specifies that this role is the default role for all users, should they not meet the requirements of another role. The initiator setting is the role assigned to a user when they open the InfoPath form for the first time.

Another point of interest is that roles are assessed on a top-down approach, however, you can not change the ordering of roles from within the InfoPath IDE. In order to change the ordering of roles, should you be required to, you must open the manifest.xsf and manually reorder the <xsf:role /> elements.