Tuesday, September 26, 2017

As you probably know Codeplex will be shut down soon. I used Codeplex many years for hosting Camlex project – open source library for creating dynamic CAML queries for Sharepoint by C# lambda expressions. Migration guide available on Codeplex says how to move source code to the Github, but unfortunately it doesn’t mention how to move issues and discussions. In this post I will share my experience of how to migrate issues and discussions from Codeplex to Github.

For migrating issues I used Codeplex-Issues-Importer Python script which worked quite well: it added issues with Codeplex label and closed those issues which were closed on Codeplex. But for discussions it was not so straightforward. First of all in Github there are no such thing as “discussion” as in Codeplex, so I decided to move them to Github issues with “Discussion: [Title]” prefix. In order to perform migration itself I made fork of Codeplex-Issues-Importer and modified it so it started to parse Codeplex discussions instead of issues and then save them into Github as issue. Fork can be found here: https://github.com/sadomovalex/Codeplex-Issues-Importer. Script is not perfect but probably will be enough just for keeping old discussions in migrated project. Result of migration can be checked here: https://github.com/sadomovalex/camlex/issues?page=2&q=is%3Aissue+is%3Aclosed.

Monday, September 4, 2017

Sliding session allows user to use site without being reauthenticated if last action was done less than configured session lifetime. In Sharepoint 2013 FBA the following parameters of security token service config are used for setting session lifetime:

CookieLifetime

FormsTokenLifeTime

LogonTokenCacheExpirationWindow

They are well described in the following article SharePoint 2013 authentication lifetime settings and I won’t repeat it here. The problem is that when you use persistent cookies (i.e. those which are stored on client’s side) only CookieLifetime are actually used. Other 2 parameters are ignored and sliding sessions doesn’t work, i.e. regardless of whether user made actions on the site or not he will be logged out after cookies will be expired. Persistent cookies can be set e.g. if user checked “Remember Me” checkbox on the login page:

So is it possible to have sliding expiration sessions when persistent cookies are used? The answer is yes, but in order to do that we will need custom HTTP module which will renew token on each request:

In the module we subscribe on SessionAuthenticationModule.SessionSecurityTokenReceived event (lines 5-6) and in event handler we renew token with extended ValidFrom and ValidTo properties (lines 36-42) which are set from CookieLifetime property of security token service config (lines 29-34) so you may continue configure it from PowerShell.

Then we need to install this module by adding dll to the GAC and the following line to the web.config <modules> section:

Thursday, August 24, 2017

If you need to make sub request from your Sharepoint site you can do it like this (in this post we will assume that we make sub requests to the same Sharepoint site):

1: var request = (HttpWebRequest)WebRequest.Create(url);

2: request.Credentials = CredentialCache.DefaultNetworkCredentials;

3: var response = (HttpWebResponse)request.GetResponse();

This code will work for Windows authentication – on receiver’s side if you will check SPContext.Current.Web.CurrentUser it will be the same as on sender’s side. But if the same code will run under FBA zone SPContext.Current.Web.CurrentUser will be null on receiver’s side. In order to force Sharepoint to execute the code under the same user also in FBA zone we need to share cookies:

In this example we assume that site works both with Windows and FBA zones and that Windows authentication is used on Default zone. After that SPContext.Current.Web.CurrentUser will be also correct on receiver’s side for FBA zone.

In order to create AD group programmatically we can use DirectoryServices .Net assembly. Here is the code which create domain global group:

1:string groupName = "...";

2: var de = new DirectoryEntry("LDAP://...");

3: var group = de.Children.Add("CN=" + groupName, "group");

4: group.Properties["samAccountName"].Value = groupName;

5: group.CommitChanges();

6:returntrue;

If we want to create Domain local group we need to set one more property for created group: groupType. Value of this property should be created as bitmask from the following values (see ADS_GROUP_TYPE_ENUM enumeration):

The reason is that by default C# will cast value (local ? 0x00000004 : 0x00000002) | 0x80000000 as long and will pass 2147483652 to the groupType property which is incorrect value here. In order to avoid this error we need to pass int value to this property, i.e. in our code we should explicitly cast it to int – in this case it will pass negative value -2147483644 there:

Here in order to write results to the log file I used approach described in the following post: Write output to the file in PowerShell. And it is quite straightforward to rewrite this script for Sharepoint Online (see article provided above for Sharepoint Online). Hope it will help someone.

About Me

I've created this blog for sharing my technical experience in software engineering. Most of posts will be dedicated to Sharepoint. But I will write also about another areas of software development for .Net platform. Hope it will be useful and will help you in your work.