Adventure in SPWonderland

Take apart and put back together

NAVIGATION - SEARCH

List Windows Groups in a SharePoint site and convert to DirectoryEntry

 

On a Claims enabled site I needed to get a Windows DirectoryEntry object for each group and list its members

Using the LDAP Sid syntax and the ADSI operator allows for a quick lookup to AD

$ClaimMan=Get-SPClaimProviderManager

$web=get-spweb http://flxdev2010:25555/sitecol1/sub6/Test3

# Get User List

$Users=$web.RoleAssignments  | % { $_.Member.Users }

# Filter to get only windows groups – return Sid’s

$WindowsGroups= $Users | ? { $_.IsDomainGroup -eq $true
        -and $ClaimMan.DecodeClaim($_.UserLogin).OriginalIssuer -eq "Windows"}  | % { $ClaimMan.DecodeClaim($_.UserLogin).Value }

# RAW Sids here
$WindowsGroups

# DirectoryEntry list here
$GroupEntries=$WindowsGroups | % { [ADSI]"LDAP://<SID=$($_)>"  }

# List members of group
$GroupEntries | % { $_.Properties["member"] }

SPClaimsUtility.AuthenticateFormsUser Invalid XML Error

 

Hit a strange error that Google turned up blank on.

I had a password reset page that took some encrypted parameters and used SPClaimsUtility.AuthenticateFormsUser to log the user in and set the session token.

This code

Uri appliesTo = new Uri(Page.Request.Url.AbsoluteUri);

// Set the session token
SPClaimsUtility.AuthenticateFormsUser(appliesTo,user.UserName, txtNewPassword.Text);
would fail with a an invalid XML Error

System.Xml.XmlUtf8RawTextWriter.InvalidXmlChar(Int32 ch, Byte* pDst, Boolean entitize) +2670818
   System.Xml.XmlUtf8RawTextWriter.WriteElementTextBlock(Char* pSrc, Char* pSrcEnd) +5042301
   System.Xml.XmlUtf8RawTextWriter.WriteString(String text) +85
   System.Xml.XmlWellFormedWriter.WriteValue(String value) +1959831
   System.Xml.XmlWrappedWriter.WriteValue(String value) +17
   Microsoft.SharePoint.IdentityModel.SPTokenCache.GetBytesForSessionToken(String cookieContents) +123
   Microsoft.SharePoint.IdentityModel.SPTokenCache.WriteToken(SessionSecurityToken sessionToken) +304
   Microsoft.IdentityModel.Web.SessionAuthenticationModule.WriteSessionTokenToCookie(SessionSecurityToken sessionToken) +136
   Microsoft.SharePoint.IdentityModel.SPSessionAuthenticationModule.AuthenticateSessionSecurityToken(SessionSecurityToken sessionToken, Boolean writeCookie) +40
   Microsoft.SharePoint.IdentityModel.SPFederationAuthenticationModule.SetPrincipalAndWriteSessionToken(SecurityToken securityToken, SPSessionTokenWriteType writeOperationType) +485

 

The problem happens because the SPTokenCache is writing the tokenreference claim into an custom XML format.

The tokenreference contains, among other things, the AppliesTo Url.

XML has issues with characters outside a strict range including lower or higher Ascii characters.

The mistake i made was using Page.Request.Url.AbsoluteUri which includes the parameters passed to the page,  this included lower Ascii characters as part of the encrypted string (now this could be BASE64 encoded to avoid that).

The fix is to pass in only the current Web Url

 Uri appliesTo = new Uri(SPContext.Current.Web.Url);             
 // Set the session token
SPClaimsUtility.AuthenticateFormsUser(appliesTo,user.UserName, txtNewPassword.Text);

Turn on tracing in SharePoint Diagnostics Studio

 

If you are getting a problem in SharePoint Diagnostics studio (part of the SharePoint Administration toolkit ) it can be useful to turn on tracing for the app.

Create a file called spdiag.exe.config in the same directory as spdiag.exe and put this in it

<configuration>
    <system.diagnostics>
        <trace autoflush="true" indentsize="4">
            <listeners>
                <add name="TextListener"
                    type="System.Diagnostics.TextWriterTraceListener"
                    initializeData="trace.log" />
            <remove name="Default" />
            </listeners>
        </trace>
    </system.diagnostics>
</configuration>

 

When you run SPDiag you will get a pretty detailed trace file generated.  For some reason this app tends to log exceptions rather than display them in the UI.

This helped me track down a blank report that was actually throwing an error behind the scenes.

System.Data.SqlClient.SqlException: Invalid object name 'TVF_RequestUsageAggregate_LogTime'.
   at System.Data.SqlClient.SqlConnection.OnError(SqlException exception, Boolean breakConnection)
   at System.Data.SqlClient.TdsParser.ThrowExceptionAndWarning(TdsParserStateObject stateObj)
   at System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj)
   at System.Data.SqlClient.SqlDataReader.ConsumeMetaData()
   at System.Data.SqlClient.SqlDataReader.get_MetaData()
   at System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString)
   at System.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean async)

Running a 32bit Application alongside SharePoint 2013 problems

 

I’ve just being doing a POC with SharePoint 2013 and I needed to quickly get a ASP.NET app running on IIS on the same machine that hosted SharePoint.

This app had a dependency 32 bit encryption DLL that I could not find a 64bit version of so I needed to run it in 32bit mode and also Classic mode as I didn’t want to mess with web.config changes.

So to get this running quickly I did the following

From a command line

cd %systemroot%\system32\inetsrv

appcmd.exe set apppool "MyAppPool" /enable32BitAppOnWin64:true
appcmd.exe set apppool "MyAppPool" /ManagedPipeLineMode:Classic
appcmd recycle apppool "MyAppPool"

You could easily use the UI to set the two properties Enable 32bit Applications and Managed Pipeline Mode Classic

image

I’ve done this before so I figured life would be good but no, when browsing the site I got the dreaded 503 Service Unavailable Error.

This generally means the AppPool  had a problem starting up and normally its a messed up web.config, section out of place, duplicate handlers, invalid XML, invalid credentials, that kind of thing.

In this case the event logs were clear. IIS was not able to load a 64bit DLL into the 32bit process.

Event Log Error Event ID 2282

The Module DLL 'C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\15\isapi\spnativerequestmodule.dll' could not be loaded due to a configuration problem. The current configuration only supports loading images built for a x86 processor architecture. The data field contains the error number. To learn more about this issue, including how to troubleshooting this kind of processor architecture mismatch error, see http://go.microsoft.com/fwlink/?LinkId=29349.

The finger points directly to a new ISAPI module in SharePoint 2013 and its stopping our 32 site from loading. Probably part of the new Request Management piece in SP2013 (http://blogs.technet.com/b/speschka/archive/2012/09/14/working-with-request-manager-in-sharepoint-2013.aspx)

Yeah fine but why the **** is this getting loaded in a non SharePoint site.

In IIS 7.x there are global (i.e. loaded into every AppPool) native ISAPI modules are loaded from the GlobalModules section, however IIS fully supports conditionally loading an ISAPI module depending on if its a 32 or 64 bit, managed or classic pipeline or even specific WebApplication’s

You can check the GlobalModules section in the file ApplicationHost.config in %systemroot%\system32\inetsrv\config
or list them with

appcmd list config  /section:globalmodules

Example Section:

<add name="ManagedEngineV4.0_32bit" image="C:\Windows\Microsoft.NET\Framework\v4.0.30319\webengine4.dll" preCondition="integratedMode,runtimeVersionv4.0,bitness32" />
           <add name="ManagedEngineV4.0_64bit" image="C:\Windows\Microsoft.NET\Framework64\v4.0.30319\webengine4.dll" preCondition="integratedMode,runtimeVersionv4.0,bitness64" />

If we check the SharePoint module it has no conditions listed, some developer slackness there as the OWSSVR.DLL entry does have some WebApplication preconditions listed.

<add name="SPNativeRequestModule" image="C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\15\isapi\spnativerequestmodule.dll"  />         

We can apply a quick fix using this command

appcmd.exe set config -section:system.webServer/globalModules /[name='SPNativeRequestModule'].preCondition:integratedMode,bitness64

Or you can manually enter the preCondition entry in the ApplicationHost.config file

<add name="SPNativeRequestModule" image="C:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\15\isapi\spnativerequestmodule.dll" preCondition="integratedMode,bitness64" />

With that in place the 32bit Web Application loaded with no other problems.

I’d class this as a bug as it completely breaks 32bit apps for no good reason.

Update User Emails in SharePoint from Active Directory

 

With SharePoint once a user is added to a SharePoint site the users email is saved at that point in time and only updated if you have the User Profile Service setup and running in which case a timer job updates user information in all site collections in the Farm.

Sometimes farms are created that stand alone and do not have the User Profile service setup or it might be a foundation Farm which has no User Profile Service. In that case this script might be useful.

It gets the Email address from AD for every user in all site collections within a Web Application and updates it if needed.

From a Powershell prompt

To Report on out of date  user emails
  .\FixUserEmails.ps1 http://sharepointurl

To update emails 
  .\FixUserEmails.ps1 http://sharepointurl $true

 

Should work for 2007 and 2010.

Its not guaranteed to work across multiple domains as the sAMAccountName attribute does not contain the domain, otherwise let me know of any issues.

FixUserEmails.zip (2.82 KB)

SharePoint 2010 EU Cookie Law Notification Control

 

I’ve just released a SharePoint 2010 solution for external SharePoint sites that need to comply with EU notification rules.

The control is activated on each Web Application and displays a message at the top of every page for each user until they click the confirm button. The confirm button stores a cookie which is detected on further page views and does not display if its detected.

This control allows active consent rather than implied consent.

Tested in SharePoint 2010 Foundation, 2010 Server, IE8/9, Chrome, Firefox.

Download from CodePlex: SharePoint 2010 Cookie Approval

TeamSiteTopPage

Case Sensitive MindF**k Part 1 SharePoint not indexing TWiki

So we’re setting up a crawl of a TWiki site as one source in a suite of content sources.

So far so good, once the authentication was sorted we noticed a problem, only the root Url of the site was getting crawled.

Various ideas were thrown around about nofollow and noindex attributes but we couldn’t find anything wrong with our configuration and nothing seemed to fit the problem.

I noticed that this particular TWiki installation was case sensitive to Urls by accident (thought those days were gone, configurable apparently) and that got me thinking.

By kicking a crawl off i noticed that SharePoint was requesting lower case urls from the Site for every link on the home page getting a 404 and stopping.

Ok penny drops but why is SharePoint sending a lower case url, well… this is by design as part of the crawler’s normalization of urls (http://blogs.msdn.com/b/enterprisesearch/archive/2010/07/09/crawling-case-sensitive-repositories-using-sharepoint-server-2010.aspx)

In 2010 if you’re setting up a crawl rule that checkbox you’ve ignored called Match Case (badly named surely Preserve Url Casing would get the point across better) just needs to be set and viola the crawler will preserve the case of Urls it requests.

Fix: Azure Dev Environment not starting

 

So we have a development VM thats pretty fully loaded with software, Sharepoint 2010, Project Server 2010 and CRM 2011.

For some reason the First Azure project on this machine refused to deploy to the local development App Fabric. The deployment hung and never completed.

 Do You Want to Wait

StartWindowsAzure

 

Nothing was posted in the event logs but there were items in the VS output screen about failing to write to the logs. Nice.

LogFiles

A search for those files found lots of Azure log folders in %localappdata%\dftmp

 LogfileLocation

In DFAgentLogs and the DFAgent.log file I found this

[2011/10/13, 10:46:12.145,  INFO, 00011572] There is already a listener on IP endpoint 0.0.0.0:808.  Make sure that you are not trying to use this endpoint multiple times in your application and that there are no other applications listening on this endpoint.
[2011/10/13, 10:46:12.639,  INFO, 00011572]    at System.ServiceModel.Channels.SocketConnectionListener.Listen()
   at System.ServiceModel.Channels.BufferedConnectionListener.Listen()
   at System.ServiceModel.Channels.ExclusiveTcpTransportManager.OnOpen()
   at System.ServiceModel.Channels.TransportManager.Open..

 

Now we’re getting somewhere, the App Fabric Development Agent is trying to listen on port 808 and failing as another process has this port in use

A netstat –ano command shows the process id that is listening on that port

NetStat

The Tasklist command tasklist /fi “PID eq 11400” shows that an exe call SMSVCHost.exe is listening on port 808

SMSvcHost

Thats the Net.TCP Port Sharing service. So the port sharing service is stopping a port being used. Marvellous.

SMSVCHostService

I’m not sure which of the installed software set that service to automatically start.

After stopping the service and restarting the Development Fabric the deployment succeeded.

Fix for Zune Error 80040154


If you've installed Zune on a Server OS like Windows 2008 by running the zune-x64.msi directly as shown by Rob Mensching
http://robmensching.com/blog/posts/2009/9/12/How-to-install-Zune-software-on-Windows-2008-R2 you probably will get error 80040154 when checking for phone updates in Zune

The error means a COM component is not registered, its looking for a component with a CLSID of {31055FF4-9B90-42D6-9672-468E3ADE9583}

To fix this in the Zune Packages directory (where you ran the Zune install from) run zunewmdu-x64 (or zunewmdu-x86.msi) as Administrator and you should be able to update your Windows 7 Phone

 

 

 

 

SPEndpointAddressNotFoundException error in Dashboard Designer

 

When using PerformancePoint Designer in SharePoint 2010 and trying to add a new item say a SQL Server connection you might get the error 'An Unexpected Error Occured. An error has been logged for the Administrator'

If you check the Event log on your client machine you should find a more detailed but equally cryptic error.

An unexpected error occurred. Error 15568.

Exception details:

Microsoft.SharePoint.SPEndpointAddressNotFoundException: There are no addresses available for this application.

at Microsoft.SharePoint.SPRoundRobinServiceLoadBalancer.BeginOperation()

at Microsoft.PerformancePoint.Scorecards.BIMonitoringServiceApplicationProxy.GetBalancerContext()

at Microsoft.PerformancePoint.Scorecards.BIMonitoringServiceApplicationProxy.ExecuteOnChannel(CodeBlock codeBlock)

 

First check in Central Administration check you have a PerformancePoint Services application created.

My problem was that although the services application was created the service instance itself was not running. Goto Central Admin - System Settings - Manage Services on Server and make sure the PerformancePoint service is started or start it youself.

Why you are not given the option in the Services App to do this automatically is a mystery to me.