SharePoint Active Directory Node Limit is hard coded! – EditDSServer.aspx

Since no one answered my question on twitter, I went back to trying
to figure this out on my own.  When you are editing the AD Connection on
the editdsserver.aspx you may run into an issue with not seeing all the
nodes in an OU.  Why?  Well, its because there is a limit on the number
of nodes that are queried.  One may ask…"can I change this"?

The
answer is no. You can change the timeouts in various different ways,
but there is NO WAY to change the node limit.  Why?  Because in the code
for the EditDSServer.aspx page, you will find a method called
"_DoLdapDirectorySearch".  This has a HARDCODED hex value of "0x3e8". 
What is that in decimal?  Its 1000.  Yes, you read that right, the hard
coded node limit is 1000 nodes.   Why is this a problem you ask?  Well,
if you needed to exclude a set of service accounts in an OU container
in your "User" OU, you won't be able to see it because it likely starts
with an "S".  If you scroll down the list, you will see the nodes end
around "M". 

Being that I am the one and only "CJG", I think to
myself, let's do this through ForeFront!  Easy enough, fire up
MIISClient.exe, change the values (b/c it DOESN'T have a limit), remove
the OUs and click Save.  I'm thinking, yeah…that was easy.  No,
Forefront will also un-check the "Users" OU when you do it like this. 
Then you lose the 1000s of users you had in the sync.  This is obviously
very bad (worse than having the service accounts in the list).

So
what do you do?  You find a blog post like this one by @mosshater that
shows you how to get at the AD connection to be able to set the naming
contexts:

http://mosshater.blogspot.com/2010/10/powershell-add-active-directory.html

This is SOOO painful…
Chris

Approval Workflow Access Denied – How to fix it!

Updated 3/18/2015:

Turns out when you migrate from one domain to another, this error pops up yet again (even after running the migrate user commands)!  Another option of fixing this is to open *each* site collection and delete the workflows.  Then deactive and active the feature.  Then you can create sites again!

Yet again, another weird bug in SharePoint 2010 that I had to track down and fix this week!  What is this?  Here's what happened:

 My customer has a few workflows created to approve important documents.  All of a sudden, these workflows stopped working with an access denied error message.  In looking at the log files, you would see this  (it's rather long):

06/27/2012 06:40:02.96     w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           ftd0    Verbose     Access Denied. Exception: System.UnauthorizedAccessException: Access is denied. (Exception from HRESULT: 0x80070005 (E_ACCESSDENIED))     at Microsoft.SharePoint.Library.SPRequestInternalClass.OpenWeb(String bstrUrl, String& pbstrServerRelativeUrl, String& pbstrTitle, String& pbstrDescription, String& pbstrTitleResourceId, String& pbstrDescriptionResourceId, Guid& pguidID, String& pbstrRequestAccessEmail, UInt32& pwebVersion, Guid& pguidScopeId, UInt32& pnAuthorID, UInt32& pnLanguage, UInt32& pnLocale, UInt16& pnTimeZone, Boolean& bTime24, Int16& pnCollation, UInt32& pnCollationLCID, Int16& pnCalendarType, Int16& pnAdjustHijriDays, Int16& pnAltCalendarType, Boolean& pbShowWeeks, Int16& pnFirstWeekOfYear, UInt32& pnFirstDayOfWeek, Int16& pnWorkDays, Int16& pnWorkDayStartHour, Int16& pnWorkD…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           ftd0    Verbose     …ayEndHour, Int16& pnMeetingCount, Int32& plFlags, Boolean& bConnectedToPortal, String& pbstrPortalUrl, String& pbstrPortalName, Int32& plWebTemplateId, Int16& pnProvisionConfig, String& pbstrDefaultTheme, String& pbstrDefaultThemeCSSUrl, String& pbstrThemedCssFolderUrl, String& pbstrAlternateCSSUrl, String& pbstrCustomizedCssFileList, String& pbstrCustomJSUrl, String& pbstrAlternateHeaderUrl, String& pbstrMasterUrl, String& pbstrCustomMasterUrl, String& pbstrSiteLogoUrl, String& pbstrSiteLogoDescription, Object& pvarUser, Boolean& pvarIsAuditor, UInt64& ppermMask, Boolean& bUserIsSiteAdmin, Boolean& bHasUniquePerm, Guid& pguidUserInfoListID, Guid& pguidUniqueNavParent, Int32& plSiteFlags, DateTime& pdtLastContentChange, DateTime& pdtLastSecurityChange, String& pbstrWelcomePage, Boolean& pb…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           ftd0    Verbose     …OverwriteMUICultures, Boolean& pbMUIEnabled, String& pbstrAlternateMUICultures, Int32& puiVersion, Int16& pnClientTag)     at Microsoft.SharePoint.Library.SPRequest.OpenWeb(String bstrUrl, String& pbstrServerRelativeUrl, String& pbstrTitle, String& pbstrDescription, String& pbstrTitleResourceId, String& pbstrDescriptionResourceId, Guid& pguidID, String& pbstrRequestAccessEmail, UInt32& pwebVersion, Guid& pguidScopeId, UInt32& pnAuthorID, UInt32& pnLanguage, UInt32& pnLocale, UInt16& pnTimeZone, Boolean& bTime24, Int16& pnCollation, UInt32& pnCollationLCID, Int16& pnCalendarType, Int16& pnAdjustHijriDays, Int16& pnAltCalendarType, Boolean& pbShowWeeks, Int16& pnFirstWeekOfYear, UInt32& pnFirstDayOfWeek, Int16& pnWorkDays, Int16& pnWorkDayStartHour, Int16& pnWorkDayEndHour, Int16& pnMeetingC…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           ftd0    Verbose     …ount, Int32& plFlags, Boolean& bConnectedToPortal, String& pbstrPortalUrl, String& pbstrPortalName, Int32& plWebTemplateId, Int16& pnProvisionConfig, String& pbstrDefaultTheme, String& pbstrDefaultThemeCSSUrl, String& pbstrThemedCssFolderUrl, String& pbstrAlternateCSSUrl, String& pbstrCustomizedCssFileList, String& pbstrCustomJSUrl, String& pbstrAlternateHeaderUrl, String& pbstrMasterUrl, String& pbstrCustomMasterUrl, String& pbstrSiteLogoUrl, String& pbstrSiteLogoDescription, Object& pvarUser, Boolean& pvarIsAuditor, UInt64& ppermMask, Boolean& bUserIsSiteAdmin, Boolean& bHasUniquePerm, Guid& pguidUserInfoListID, Guid& pguidUniqueNavParent, Int32& plSiteFlags, DateTime& pdtLastContentChange, DateTime& pdtLastSecurityChange, String& pbstrWelcomePage, Boolean& pbOverwriteMUICultures, Boolea…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           ftd0    Verbose     …n& pbMUIEnabled, String& pbstrAlternateMUICultures, Int32& puiVersion, Int16& pnClientTag).    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96     w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           8gs1    Verbose     Access Deni
ed for /contoso/_layouts/IniWrkflIP.aspx?List={b713a4ad-747e-4980-ad1c-c420d3f588b7}&ID=1&TemplateID={3cf9d212-c83d-4486-9fce-ee8d00efacbc}&Source=blah StackTrace:    at Microsoft.SharePoint.Utilities.SPUtility.HandleAccessDenied(HttpContext context)     at Microsoft.SharePoint.Utilities.SPUtility.HandleAccessDenied(Exception ex)     at Microsoft.SharePoint.Library.SPRequest.OpenWeb(String bstrUrl, String& pbstrServerRelativeUrl, String& pbstrTitle, String& pbstrDescription, String& pbstrTitleResourceId, String& pbstrDescriptionResourceId, Guid& pguidID, String& pbstrRequestAccessEmail, UInt32& pwebVersion, Guid& pguidScopeId, UInt32& pnA…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           8gs1    Verbose     …uthorID, UInt32& pnLanguage, UInt32& pnLocale, UInt16& pnTimeZone, Boolean& bTime24, Int16& pnCollation, UInt32& pnCollationLCID, Int16& pnCalendarType, Int16& pnAdjustHijriDays, Int16& pnAltCalendarType, Boolean& pbShowWeeks, Int16& pnFirstWeekOfYear, UInt32& pnFirstDayOfWeek, Int16& pnWorkDays, Int16& pnWorkDayStartHour, Int16& pnWorkDayEndHour, Int16& pnMeetingCount, Int32& plFlags, Boolean& bConnectedToPortal, String& pbstrPortalUrl, String& pbstrPortalName, Int32& plWebTemplateId, Int16& pnProvisionConfig, String& pbstrDefaultTheme, String& pbstrDefaultThemeCSSUrl, String& pbstrThemedCssFolderUrl, String& pbstrAlternateCSSUrl, String& pbstrCustomizedCssFileList, String& pbstrCustomJSUrl, String& pbstrAlternateHeaderUrl, String& pbstrMasterUrl, String& pbstrCustomMasterUrl, String& pbs…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           8gs1    Verbose     …trSiteLogoUrl, String& pbstrSiteLogoDescription, Object& pvarUser, Boolean& pvarIsAuditor, UInt64& ppermMask, Boolean& bUserIsSiteAdmin, Boolean& bHasUniquePerm, Guid& pguidUserInfoListID, Guid& pguidUniqueNavParent, Int32& plSiteFlags, DateTime& pdtLastContentChange, DateTime& pdtLastSecurityChange, String& pbstrWelcomePage, Boolean& pbOverwriteMUICultures, Boolean& pbMUIEnabled, String& pbstrAlternateMUICultures, Int32& puiVersion, Int16& pnClientTag)     at Microsoft.SharePoint.SPWeb.InitWeb()     at Microsoft.SharePoint.SPWeb.get_Title()     at Microsoft.SharePoint.SPSite.OpenWeb(Guid gWebId, Int32 mondoHint)     at Microsoft.SharePoint.Workflow.SPWinOEWSSService.GetWebForWorkflow(SPWorkflow wf, SPWorkflowUserContext runAsUser)     at Microsoft.SharePoint.Workflow.SPWinOEWSSService.get…    aed86901-9e96-4e1d-acac-32f5d8bba3d8
06/27/2012 06:40:02.96*    w3wp.exe (0x1314)                           0x2A00    SharePoint Foundation             General                           8gs1    Verbose     …_Web()     at Microsoft.SharePoint.Workflow.SPWinOEWSSService.GetWebForListItemService()     at Microsoft.SharePoint.Workflow.SPWinOEWSSService.UpdateModerationStatus(Guid id, Guid listId, SPItemKey itemKey, SPModerationStatusType newModerationStatus, String comments)     at Microsoft.Office.Workflow.Actions.SetTaskProcessItemModerationStatus.DoUpdate(ActivityExecutionContext context)     at Microsoft.SharePoint.WorkflowActions.WaitForDocumentUnlockActivity.Execute(ActivityExecutionContext executionContext)     at Microsoft.Office.Workflow.Actions.SetTaskProcessItemModerationStatus.Execute(ActivityExecutionContext context)     at System.Workflow.ComponentModel.ActivityExecutor`1.Execute(T activity, ActivityExecutionContext executionContext)     at System.Workflow.ComponentModel.ActivityExe…    aed86901-9e96-4e1d-acac-32f5d8bba3d8

Looking at the stack trace, you can see that the code is making a call to the GetWebForWorkflow method of the SPWinOEWSSService.  In reflecting this method, you will see that it can take one of three paths:

  • Execute as the system account
  • Execute as the workflow template author
  • Execute as the workflow template owner

The system account always has access, so it was obvious that this wasn't the path it was taking.  The owner seems to always be set to "-1" and no where in the massive amount of code that I reviewed did it ever get set to anything else.  That left the author as the most probably entry point.  When reviewing where the author comes from, you find a tangled set of code that really doesn't make much sense at all (hmm…SharePoint in all its glory).  After decoding the entanglement, I found that the author comes from some set of properties that end up in a object array for the SPWebWorkflow.  This array is built from a call to SPRequest.GetListItemWorkflowAsSafeArray.  This of course means that you can't go any farther into the code unless you get really fancy building a SPRequest wrapper (which can be done, but its really hard).  Because the properties are built in a somewhat OnDemand fashion, you don't really have any way of knowing when that code will be executed…and because I'm in production, I can't sit here and do IISRESET's all day long watching for some workflow related Stored Procedure via SQL Profiler.

So how did I figure out what was up with this?  Well, the hint was in the SPRequest method call name.  GetListItemWorkflowAsSafeArray.  ListItem?  Which implies the metadata for the workflow is in the list.  Which means the author info is also coming from the listlistitem.  So where do workflows get stored in a siteweb?  They get saved to the \_catlogswfpub library at the site collection root web.

In looking at this library through SharePoint Designer, you will see that when you first activate the workflow features, the files are created by THE USER who actually made the feature activation call (whether through the UI or stsadm or PowerShell).  Hmm, very poor design.

Why is it poor design?  Well, the author comes from the created field for the list item that has the workflow template defined.  In our case, this account was recently DISABLED.  When an account becomes disabled, you can't do JACK in SharePoint.  This includes executing the workflows that were
built off the template in the first place. So what are your options?

  • Delete all the files, reactivate the workflows – YOU MUST DELETE THE FILES, if you do not, the files will stay with the created field still set to the old userId (If you have ever taken any of my course, you know rule number one is "SharePoint never deleted anything").  This means you'll still have the ACCESS DENIED error even after you deactivate and re-activate the workflows
  • Try to modify the CREATED and MODIFIED columns in the list to change the SPUser (I didn't try this, but it seems like it should work)

So, have you seen this?  Probably not.  Will every SharePoint farm on the planet eventually have this issue – YES!  You won't keep accounts around forever (unless you have a very poor security policy).  So it is worthwhile to review all your site collections and check to see who the workflow files are owned by.  Hopefully you have an SPAdmin or SPFarm account that you can use to enable the workflows with.  SO…NET NET:

Never enable workflow features as a regular user, always use some SharePoint account that will never be disabled

Yuk, yuk…yuk|
Chris

 

2012 SharePoint Jokes

Time for some more SharePoint jokes!

  • What did Office Word 2010 say to SharePoint 2010 Word Automation Services?
    • When can I retire?
  • There was a party going on in the content database, and several SharePoint groups were invited.  The pick-up question of the night was…
    • What site collection you from?
  • What percentage of code is Microsoft's after installing all 3rd party components to support your business?
    • <5%
  • A security firm recently asked SharePoint customers what was their major pain with SharePoint security?  The customer replied…knowing what permissions SharePoint decides to give you at any moment in time!
  • A customer recently was migrating from Oracle Portal to SharePoint 2010. After the migration, the customer asked, where'd all my features go?
  • How did the IT Pro reset the passwords on their SharePoint Farm?
    • They reinstalled everything!
  • What did one SharePoint user tell another user…?
    • Hey, if we yell enough, we can get SharePoint Designer access!
  • On average, how many SharePoint consultant firms till you find a good one?
    • Not including MCS?
  • What will you find if you look in the recycle bin?
    • A hole
  • What happens if you program Project Service Interface (PSI)?
    • Absolutely nothing
  • How many times does it take to setup Document IDs?
    • Lost count at 100…
  • How many customer actually use Document IDs?
    • One – Microsoft
  • What happens when you setup the content type hub?
    • You get lots of errors
  • How many SharePoint developers do you need to support your business units custom needs?
    • Half of China
  • How many SharePoint MVPs earned their MVP from posting on the MSDN Forums?
    • Wait…they know what the forums are?
  • What did the Oracle WebCenter customers tell Oracle after looking at Microsoft Pricing?
    • Why do you make us pay so much?
  • Why did Seattle lose the SuperSonics? 
    • Because SharePoint Designer is FREE and Baller isn't Jewish…and lattes cost $5 and Shultz is Jewish…and neither of them are from Oklahoma!

Bad, but oh so good…
CJG

How to remove blank comments on Append Changes to Existing Text

This is a rather simple issue, but an issue none the less.  It has been covered a few times before:

The issue is that it creates a blank comment every time someone edits a versioned list item.  The reason is that it *IS* actually adding text but it is an empty DIV tag:

<DIV></DIV>

When you set the column to be plain text, it doesn't add this empty DIV tag.  Ok, so just change to plain text and everyone is happy right?  Not quite.  When users connect to the list via the Outlook option, you get a very nasty set of HTML saved to the column (even in Plain text mode):

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
<HTML>
<HEAD>
<META NAME="Generator" CONTENT="MS Exchange Server version 08.01.0240.003">
<TITLE></TITLE>
</HEAD>
<BODY>
<!– Converted from text/plain format –>
</BODY>
</HTML>

Here's what you do in the event receiver to get rid of all this mess and have it work wether it is Plain Text or Rich Text:

class ContosoEventReceiverAppendChanges : SPItemEventReceiver
{
public override void ItemUpdating(SPItemEventProperties properties)
{
base.ItemUpdating(properties);
Hashtable ht = new Hashtable();
foreach (DictionaryEntry o in properties.AfterProperties)
{
if (o.Value.ToString() == "<DIV></DIV>" || o.Value.ToString().Contains("<BODY> <!– Converted from text/plain format –> </BODY>"))
{
ht.Add(o.Key, o.Key);|
}
}
foreach (string key in ht.Keys)
{
properties.AfterProperties[key] =
"";
}}}

Powershell to deploy it:

$web = get-spweb http://sharepoint.contoso.com
$list = $web.lists["TaskTest"]
$def = $list.EventReceivers.add()
$def.Assembly = "Contoso.Common, Version=1.0.0.0, Culture=Neutral, PublicKeyToken=a61cba8dcde3eaaa";
$def.Class = "Contoso.Common.ConotosEventReceiverAppendChanges";
$def.Name = "ItemUpdated Event";
$def.Type = [Microsoft.SharePoint.SPEventReceiverTy
pe]::ItemUpdating;
$def.SequenceNumber = 1000;
$def.Synchronization = [Microsoft.SharePoint.SPEventReceiverSynchronization]::Synchronous;
$def.Update();
$web.dispose()

Enjoy,
Chris

Follow me on twitter: @givenscj

Check out the previous blog post:
https://blogs.architectingconnectedsystems.com/blogs/cjg/archive/2012/05/30/Project-Server-2010-_2D00_-Moving-Project-Sites-and-deleting-the-old-PWA-causes-issues.aspx

SharePoint Farm Full Password Reset

At a customer of mine we recently had to do a full password reset of ALL of Active Directory.  This included all user and service accounts, even the SharePoint ones.  If you have EVER had to do this, you know that if you don't change the password in SharePoint a few minutes after the change in AD, you will be forced to manually change them across soo many places its not even funny.  It turns out, we had to do a second password reset not long after the first one.  It will become a commonplace thing that ALL passwords will be reset every couple of months and therefore, changing the passwords across all the farm servers (SharePoint, FAST and SQL Server) just ain't going to cut it.

Therefore, I wrote a PowerShell script to do it!  It worked really well!  It changes every single place one could imagine to have a username and password in your farm.  I was going to post it, but decided that I would make a product out of it.  If you would like to try out this gem, send me an email and I can send you a trial:

chris@architectingconnectedsystems.com

Thanks,
Chris

Follow me on twitter: @givenscj

Check out the previous blog post:
https://blogs.architectingconnectedsystems.com/blogs/cjg/archive/2012/05/23/Office-Web-Apps-_2D00_-Word-Viewing-Service-Error.aspx

Office Web Apps – Word Viewing Service Error

All of a sudden, we started having issues with our Office Web Apps install for a set of users.  No reason, no changes, just some users can't use OWA to VIEW files (they can however edit the files in the browser).  The service account for the application pool and the word viewing app pool both have dbo on the content database in question.

Here's the errors:

User:

Word Web App cannot open this document for viewing because of an unexpected error.  To view this document, open it in Microsoft Word.

WFE:

 05/23/2012 07:56:55.17  w3wp.exe (0x32CC)                        0x310C Office Web Apps                Office Viewing Architecture    dg2s Medium   RequestDispatcher: response received for document F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em from http://servername:32843/69c32f311e164e8184803a179b32d194/Conversion.svc. d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.19  w3wp.exe (0x32CC)                        0x310C Office Web Apps                Office Viewing Architecture    b4vn Medium   Conversion response received: CantFindSourceDocument d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.19  w3wp.exe (0x32CC)                        0x310C Office Web Apps                Office Viewing Architecture    b4vi Verbose  DocumentInfoCache.RemoveDocumentInfo: docId=d=F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em&z=06EBAF2E-1684-459C-9C00-819543A2A08E1, outputFormat=_v00000000-0000-0000-0000-000000000202 d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.19  w3wp.exe (0x32CC)                        0x310C Office Web Apps                Office Viewing Architecture    vjza Medium   Librarian.OnConversionResponseReceived(F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em, Png, docdata.xml) – Response=CantFindSourceDocument, Data=NO d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.20  w3wp.exe (0x32CC)                        0x310C Office Web Apps                Office Viewing Architecture    vjzo Medium   Librarian.SetCompleted(F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em, Png, docdata.xml) – status = ConversionError d3e88a2a-977b-48df-a70a-4765c4ff1ac9

APP:

05/23/2012 07:56:55.57  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Viewing Architecture    bv6l Medium   DownloadManager: Starting download for document F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em. d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.57  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Performance Tracing     dcw3 Verbose  PerfCounterAverageTimer started: WssStorageReadTime d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.57  w3wp.exe (0x1330)                        0x0B6C SharePoint Foundation          General                        6t8j Verbose  Site lookup by id found the typical site /training. d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.57  w3wp.exe (0x1330)                        0x0B6C SharePoint Foundation          General                        8kh7 High     Cannot complete this action.  Please try again. d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)                        0x0B6C SharePoint Foundation          General                        8kh7 High     Stack trace: onetutil.dll: (unresolved symbol, module offset=00000000000A2551) at 0x000007FEF0142551 onetutil.dll: (unresolved symbol, module offset=00000000000A3711) at 0x000007FEF0143711 owssvr.dll: (unresolved symbol, module offset=0000000000009212) at 0x000007FEF0399212 owssvr.dll: (unresolved symbol, module offset=0000000000044378) at 0x000007FEF03D4378 mscorwks.dll: (unresolved symbol, module offset=00000000002CB6D7) at 0x000007FEF9BFB6D7 Microsoft.SharePoint.Library.ni.dll: (unresolved symbol, module offset=00000000000E5128) at 0x000007FEF2D85128 Microsoft.SharePoint.ni.dll: (unresolved symbol, module offset=0000000001AB43D0) at 0x000007FEE0AA43D0 Microsoft.SharePoint.ni.dll: (unresolved symbol, module offset=0000000001AA811D) at 0x000007FEE0A9811D Microsoft.SharePoint.ni.dll: (unre… d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58* w3wp.exe (0x1330)                        0x0B6C SharePoint Foundation          General                        8kh7 High     …solved symbol, module offset=0000000001AADC71) at 0x000007FEE0A9DC71 Microsoft.SharePoint.ni.dll: (unresolved symbol, module offset=0000000001AA2A25) at 0x000007FEE0A92A25 Microsoft.SharePoint.ni.dll: (unresolved symbol, module offset=0000000001AA4717) at 0x000007FEE0A94717 Microsoft.SharePoint.ni.dll: (unresolved symbol, module offset=0000000001AA46A2) at 0x000007FEE0A946A2  d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)            &nbs
p;           0x0B6C Office Web Apps                Office Viewing Architecture    ekp1 Medium   No SPFile found for Id 06ebaf2e-1684-459c-9c00-819543a2a08e d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Viewing Architecture    ekp3 Medium   SharepointReaderAsync: No SPFile provided d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Performance Tracing     a495 Verbose  PerfCounterAverageTimer stopped: WssStorageReadTime, elapsed time = 20 milliseconds d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Viewing Architecture    bv6p Unexpected Exception thrown downloading file C:WindowsTEMPwaccache69c32f31-1e16-4e81-8480-3a179b32d194domainuserca171873-6de3-4dd4-abef-09d23996d26coutput.docx: System.ArgumentException: SharepointReaderAsync: no SPFile     at Microsoft.Office.Web.Environment.Sharepoint.SharepointReaderAsync.End()     at Microsoft.Office.Web.Conversion.Framework.DownloadManager.OnFileReadComplete(IAsyncResult ar) d3e88a2a-977b-48df-a70a-4765c4ff1ac9
05/23/2012 07:56:55.58  w3wp.exe (0x1330)                        0x0B6C Office Web Apps                Office Viewing Architecture    fvj9 Unexpected DownloadManager: Download FAILED for document F4813f0a0691d4d61a109e9ab86a17815m4d776f4fd83844328210cf1c84e667cbm06ebaf2e1684459c9c00819543a2a08em; Time spent: 24ms. d3e88a2a-977b-48df-a70a-4765c4ff1ac9

The only possible hints lie in the users access (this says it is request view and edit access but the user doesn't have it):

05/23/2012 07:56:54.20  w3wp.exe (0x32CC)                        0x2B94 SharePoint Foundation          General                        ewn8 Verbose  OriginalPermissionMask check failed. asking for 0x00000005, have 0xB008431041 9806faaf-ad37-406f-9164-5705a9aca938

You'll also find several errors about configuration settings missing for the Word Viewing settings:

05/23/2012 07:56:54.30  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting C2ROFFERENABLED 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.30  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting C2ROFFERENABLED but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.30  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting WLSIAOFFERENABLED 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.30  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting WLSIAOFFERENABLED but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.31  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting USEPARENTHELPFUNCTION 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.31  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting USEPARENTHELPFUNCTION but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.31  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting SHOWFEEDBACKLINK 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.31  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting SHOWFEEDBACKLINK but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting HIDETITLE 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps     
           Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting HIDETITLE but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting MACOFFICETRIALOFFERENABLED 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting MACOFFICETRIALOFFERENABLED but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting TRIMOICBUTTONSIFUNAVAILABLE 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbx0 Verbose  Tried to obtain setting TRIMOICBUTTONSIFUNAVAILABLE but it does not exist in the list of known settings for this environment. 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting WORDWEBAPPSHORTRESOURCENAME 9806faaf-ad37-406f-9164-5705a9aca938
05/23/2012 07:56:54.33  w3wp.exe (0x32CC)                        0x2B94 Office Web Apps                Office Web Apps Configuration  bbw9 Verbose  Trying to get setting WORDWEBAPPFULLRESOURCENAME 9806faaf-ad37-406f-9164-5705a9aca938

What have I done so far?  Here's the things I have tried: 

  1. I created a new Word Viewing Service and set it as the default service application.  Had the user retry…the documents still didn't display in OWA and I still get all the wonderful OWA settings are missing messages (so the messages can be ignored) – NO GO
  2. I gave the user contribute access, had them re-try…still didn't display in OWA, but at least a new button showed up on the error that lets them "Open in Word" (realized this happens after the second attempt to open the file) – NO GO
  3. Last ditch effort, added the app pool for the OWA conversion service to the local WSS_ADMIN_WPG…NO GO.
  4. Made the user a site collection admin – NO GO  

Weird that it only applies to a small set of users.  It shouldn't matter that they just have View Only rights to the file, it should open in OWA…again editing works just fine…

Sooo…how did I fix this?  I went to the handy SQL Profiler tool and watched the SQL traffic.  I re-run all the queries and looked at all the results sets that were returned.  I opened the OWA dlls in Reflecter and explored every method call.  I found the "no SPFile" returned set of code, everything looks file, but, it is the hint that I was looking for.  Stepping back, one should ask…why is the file not being returned?  It is there, but…it isn't?  In looking at the result sets, I found something interesting.  Once upon a time, users had enabled the DocumentID feature of sharepoint.  This assigned document ids to some of the documents.  They also are using this tool called "CopyPaste".  When copying a record from one site collection to another, the document ID values were being replicated to the new location and metadata of the files.  When OWA makes the call to get the file, it is going through the SharePoint APIs and in this case, the document ID is wrong and the site that used to hold the file is gone (or in some cases not accessible by the user because we removed their permissions)!  Document IDs suck and this is just another reason to use my SharePoint Durable Urls tool (http://www.sharepointdurableurls.com). That means…if you hit the document id link for the file, you get simple html that says "File Not Found".  BINGO!  Now…how to remove the DocumentID residual?  Here's what I did:

foreach($li in $list.items)
{
$docid = $li["Document ID"]

if ($docid)
{
"Found doc id in " + $li["Name"]
"ID is: $docid"

$li.file.checkout()
$li["Document ID"] = ""
$li.update()
$li.file.checkin("Removed Document ID")
}
}

Yet another case of the code making one call (View is using the DocumentID redirect) in one instance and another in another instance (Editing does not use the DocumentID redirect).  Very annoying.

Enjoy!
Chris

Follow me on twitter: @givenscj

Check out the previous blog post:
https://blogs.architectingconnectedsystems.com/blogs/cjg/archive/2012/05/18/Announcing-_2D00_-ACS-Rebate-and-Charity-Event.aspx

HUGE Permissions bug with Import-SPWeb -includeusersecurity

The Export-SPWeb and Import-SPWeb is a tool for moving sites around, but with all the changes that have occured with SharePoint 2010 over the past two years, it seems some of the plumbing isn't connected correctly.

One of the issues we were seeing is that after importing a site, users are able to get to the site, but not to libraries underneath the site.  You would see ULS logs like:

OriginalPermissionMask check failed. asking for 0x00020000, have 0x00000000 

Nice list of the perm masks for reference:
http://social.msdn.microsoft.com/Forums/en/sharepointdevelopment/thread/c32bc150-7249-423d-8018-d2f23afc1f3b

Exception: System.UnauthorizedAccessException: Attempted to perform an unauthorized operation.. 

Access Denied for SITEURL. StackTrace:    at Microsoft.SharePoint.Utilities.SPUtility.HandleAccessDenied(HttpContext context)     at Microsoft.SharePoint.Utilities.SPUtility.HandleAccessDenied(Exception ex)     at Microsoft.SharePoint.SPWeb.GetWebPartPageContent(Uri pageUrl, Int32 pageVersion, PageView requestedView, HttpContext context, Boolean forRender, Boolean includeHidden, Boolean mainFileRequest, Boolean fetchDependencyInformation, Boolean& ghostedPage, Byte& verGhostedPage, String& siteRoot, Guid& siteId, Int64& bytes, Guid& docId, UInt32& docVersion, String& timeLastModified, Byte& level, Object& buildDependencySetData, UInt32& dependencyCount, Object& buildDependencies, SPWebPartCollectionInitialState& initialState, Object& oMultipleMeetingDoclibRootFolders, String& redirectUrl, Boolean& ObjectIsList, Guid& listId)     at Microsoft.SharePoint.ApplicationRuntime.SPRequestModuleData.FetchWebPartPageInformationForInit(HttpContext context, SPWeb spweb, Boolean mainFileRequest, String path, Boolean impersonate, Boolean& fGhostedPage, Byte& verGhostedPage, Guid& docId, UInt32& docVersion, String& timeLastModified, SPFileLevel& spLevel, String& masterPageUrl, String& customMasterPageUrl, String& webUrl, String& siteUrl, Guid& siteId, Object& buildDependencySetData, SPWebPartCollectionInitialState& initialState, String& siteRoot, String& redirectUrl, Object& oMultipleMeetingDoclibRootFolders, Boolean& objectIsList, Guid& listId, Int64& bytes)     at Microsoft.SharePoint.ApplicationRuntime.SPRequestModuleData.GetFileForRequest(HttpContext context, SPWeb web, Boolean exclusion, String virtualPath)     at Microsoft.SharePoint.ApplicationRuntime.SPRequestModule.InitContextWeb(HttpContext context, SPWeb web)     at Microsoft.SharePoint.WebControls.SPControl.SPWebEnsureSPControl(HttpContext context)     at Microsoft.SharePoint.ApplicationRuntime.SPRequestModule.GetContextWeb(HttpContext context)     at Microsoft.SharePoint.ApplicationRuntime.SPRequestModule.PostResolveRequestCacheHandler(Object oSender, EventArgs ea)     at System.Web.HttpApplication.SyncEventExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute()     at System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously)     at System.Web.HttpApplication.PipelineStepManager.ResumeSteps(Exception error)     at System.Web.HttpApplication.BeginProcessRequestNotification(HttpContext context, AsyncCallback cb)     at System.Web.HttpRuntime.ProcessRequestNotificationPrivate(IIS7WorkerRequest wr, HttpContext context)     at System.Web.Hosting.PipelineRuntime.ProcessRequestNotificationHelper(IntPtr managedHttpContext, IntPtr nativeRequestContext, IntPtr moduleData, Int32 flags)     at System.Web.Hosting.PipelineRuntime.ProcessRequestNotification(IntPtr managedHttpContext, IntPtr nativeRequestContext, IntPtr moduleData, Int32 flags)     at System.Web.Hosting.PipelineRuntime.ProcessRequestNotificationHelper(IntPtr managedHttpContext, IntPtr nativeRequestContext, IntPtr moduleData, Int32 flags)     at System.Web.Hosting.PipelineRuntime.ProcessRequestNotification(IntPtr managedHttpContext, IntPtr nativeRequestContext, IntPtr moduleDa…

Looking at the permissions for the library (Site Actions->Site Permissions OR Library->Library Permissions), you WOULD see what you are supposed to see as far as permissons are concerned (even the CheckPermissions tool shows what we want).  However, looks are DECEIVEING!  Also, when we try to break permissions, it would continue to show that the list was inheriting from the parent.  No errors would be thrown in the UI.  When using powershell and tracing the verbose calls in ULSViewer you would actually see some more revealing details:

05/10/2012 09:23:21.29 PowerShell.exe (0x1180) 0x0D3C SharePoint Foundation General bj8s Medium setSecurityScopeUnique: start 
05/10/2012 09:23:21.29 PowerShell.exe (0x1180) 0x0D3C SharePoint Foundation General bj8t Medium setSecurityScopeUnique: already unique 
05/10/2012 09:23:21.29 PowerShell.exe (0x1180) 0x0D3C SharePoint Foundation General bj8w Medium setSecurityScopeUnique: finished 

Notice the second line:  "Already unique"…WTF…no its not!  The UI shows it is inheriting permissions!  So what is going on here?

Turning on the handy SQL Profiler, I did the following powershell on a "working" list:

$web = get-spweb http://blah
$list = $web.lists["Project Documents"]
$list.BreakInheritance($true, $false)
$list.Update()

What you see in profiler is a call to:

declare @p15 uniqueidentifier
set @p15='4EE7D0C0-0133-4600-A96E-53BD0D133DEF'
exec proc_SecChangeToUniqueScope @SiteId='EFAF8E96-FA9F-4816-A965-CE7A8C6ED8AC',@WebId='E504097A-2BA1-400F-BCC2-5DE6B32E8615',@OldScopeId='3FB9F8DA-A957-4B82-B4AA-FECB3B1B4551',@CopyFromScopeId='3FB9F8DA-A957-4B82-B4AA-FECB3B1B4551',@Url=N'asi/Shared Documents',@DocId='00000000-0000-0000-0000-000000000000',@bIsWeb=0,@UserId=1073741823,@CopyAnonymousMask=1,@CopyRoleAssignments=1,@ClearSubScopes=0,@bBreakBySiteOwner=0,@ReturnAuditMask=1,@MaxScopeInList=50000,@NewScopeId=@p15 output,@RequestGuid='00000000-0000-0000-0000-000000000000'
select @p15

When performing the same operation on a "broken" list (remember, from an imported web), you DO NOT see this call made.  So I decided, lets look at that stored procedure and see what it does.  The SP will actually look at the "Perms" table for a "ScopeId", then it will replicate what it needs in all the related tables to create a copy of a parent scope (actually doesn't have to be a parent, but the SharePoint team doesn't let us do this through the UIs – wouldn't that be handy!).

So what is the problem?  Well…the problem centers on that pesky "ScopeId".  What is happening is that SharePoint has TWO ways to get permissions information:

  1. Get the scopeid from the AllLists table (using urls or ids)
  2. Get the scopeid from the perms table (using urls or ids)

UPDATE:  There is also a scopeid on the AllDocs table that also gets out of whack!

In some places the object model and the "obfuscated" SPRequest COM objects are making two different calls!  One will look at the AllLists table, the other will look
at the Perms table.  This is the BUG.  ALL access APIs are using the "Perms" table, all UI APIs (including the CheckPermissions tool) are using the "AllLists" table.  They should look at the same place!  What is happening is the scopeID of imported objects is being set to the parent webs scopeID!  So even though the UI shows you what you WANT to see, the internals think that the permissions are that of the web's parent web!  THAT'S NOT GOOD!

How do you fix this?  Your not going to like the answer…none of the object model calls would reset the scopeid of the lists or webs.  I had to go into the database and reset the mapping of the scopeIds.  Once I did this, BAM!  Everything started working again…

Second big bug I have found in SharePoint 2010 in the last two weeks.

SQL Queries to help you find things:

Find List Scopes:

SELECT tp_Title, tp_ScopeId
FROM
[AllLists]
where

tp_WebId
= 'GUID'

Find Doc Scopes:

SELECT WebId, DirName, LeafName, scopeid
FROM
[AllDocs]
where DirName like '%blah%'

Find Web Scopes:

SELECT ID, FullUrl, scopeid
FROM
[AllWebs]
where fullurl like '%blah%'

Find Scope Permissions:

declare @scopeid as varchar(max)
set @scopeid = 'A3A5D2C8-5624-4E2A-BE7A-7D51C26DB081'

SELECT *
FROM
[Perms]
where scopeid in (@scopeid
)

select *
FROM RoleAssignment ra,
Roles r
where ScopeId =
@scopeid
and ra.RoleId = r.RoleId

Grrr….
Chris

Follow me on twitter: @givenscj

Check out the previous blog post:
https://blogs.architectingconnectedsystems.com/blogs/cjg/archive/2012/04/20/ATTENTION_3A00_-Database-Leak-in-SharePoint-2010_210021002100_.aspx

Project Server PSI WCF bug – WSEC_CAT_UID and WSEC_GRP_UID

At one of my customers we are automating the project and project site creation for Project Server 2010.  As part of that, we wanted the proper permissions to be setup for each resource/user.  This includes making them in the "Project Manager" group and the "My Projects" and "My Resources" categories.  The code wasn't very straight forward, but I got most of it working (creating the resource and making a resource a user).  The part that doesn't work is the group and categories assignment.  Here is the code:

SvcSecurity.SecurityGroupsDataSet sgDataSet = new SvcSecurity.SecurityGroupsDataSet();
//Get the security group
SvcSecurity.SecurityGroupsDataSet sglist = securityClient.ReadGroupList();
SvcSecurity.
SecurityGroupsDataSet.SecurityGroupsRow groupDs = null;
foreach (SvcSecurity.SecurityGroupsDataSet.SecurityGroupsRow sg in sglist.SecurityGroups)
{
if (sg.WSEC_GRP_NAME == groupName)
{
groupDs = sg;|
}
}

SvcSecurity.SecurityGroupsDataSet ds = new SvcSecurity.SecurityGroupsDataSet();
// Specify which users belong to the new group.

SvcSecurity.SecurityGroupsDataSet ds = new SvcSecurity.SecurityGroupsDataSet();
// Specify which users belong to the new group.

SvcSecurity.SecurityGroupsDataSet.GroupMembersRow groupMembersRow = ds.GroupMembers.NewGroupMembersRow();
groupMembersRow.WSEC_GRP_UID = groupDs.WSEC_GRP_UID;
// Add the GUID of the resource to the group.
groupMembersRow.RES_UID = NewResGuid;
ds.GroupMembers.AddGroupMembersRow(groupMembersRow);
securityClient.SetGroups(ds);

SecurityGroupsDataSet.GroupMembersRow groupMembersRow = ds.GroupMembers.NewGroupMembersRow();
groupMembersRow.WSEC_GRP_UID = groupDs.WSEC_GRP_UID;
// Add the GUID of the resource to the group.
groupMembersRow.RES_UID = NewResGuid;
ds.GroupMembers.AddGroupMembersRow(groupMembersRow);
securityClient.SetGroups(ds);

The problem lies in the finding of the group.  The DataSet that is returned returns the WSEC_GRP_UID.  This particular column is NOT what the following AddGroupMembersRow call wants!  It actually is looking for a second GUID in the database called WSEC_GRP_GUID.  This is not returned in the PSI call and therefore, you have ZERO chance of successfully going through the PSI apis to get the id.  You end up having to query the database directly…yuk.

Anyone that develops PSI out there?  You really need to fix this…

Chris

ATTENTION: Database Leak in SharePoint 2010!!!

I have been doing a massive Oracle Portal migration, 3000+ pages of content, with a targeted subset of that in my dev envrionment at just over 3GB of content.  I noticed the other day that my development content database kept getting bigger and bigger.  Running a "dbcc checkdb" pointed me to the largest tables.  After clearing the Audit logs, EventLogs and everything else I could think of, then shrinking the database files, the databse size was still WAY bigger than what it was supposed to be (it should be 35GB, but it is currently 72GB).  The dbcc command pointed to the AllDocStreams table as the source of the problem.  I thought it possible the new web recycle bin may be the culprit, so I set out to find the root cause and prove to the community that "Redmond, we have a problem"

My first test was to create a web and then delete it over and over again.  That didn't change the row sizes in the database.  Next test was to do the same thing, only add a document to the doc library.  That didn't cause any leaks.  The last step was to enable versioning and to upload a document a few times, then delete the webs…VIOLA!  Found the leak!  Want to try this on your own…here is the PowerShell that proves that we have a big issue here:

function CheckRows($table, $conn)
{
$sql = "select count(*) as count from $table";
$cmd = new-object system.data.sqlclient.sqlcommand($sql, $conn)

$reader = $cmd.executereader()

while($reader.read())
{
$line = $reader["count"].tostring()
}

$reader.close()

"$table has " + $line + " rows"
}

function ReportRowCounts($cdb)
{

$connString = $cdb.LegacyDatabaseConnectionString

$conn = new-object system.data.sqlclient.sqlconnection
$conn.connectionstring = $connstring
$conn.open()

CheckRows "AllDocs" $conn
CheckRows "AllDocStreams" $conn
CheckRows "AllDocVersions" $conn

$conn.close()

}

function UploadFile($web)
{

$list = $web.lists["Shared Documents"]
$list.EnableModeration = $true
$list.EnableMinorVersions = $true
$list.contenttypesenabled = $true
$list.update()

$spFolder = $list.rootfolder
$spFileCollection = $spFolder.Files
$file = get-item "c:scriptsexport.zip"
$spfile = $spFileCollection.Add($file.name,$file.OpenRead(),$true)
$spfile.checkout()
$spfile.checkin("checkin")
$spfile.approve("approved")

}

$cdb = get-spcontentdatabase "WSS_Content_Contoso"
$web = get-spweb
http://www.contoso.com

ReportRowCounts($cdb)

#create a site
$subweb = $web.webs.add("Test1", "Test1", "", 1033, "STS#0", $false, $false);

ReportRowCounts($cdb)

$subweb.delete()

ReportRowCounts($cdb)

$subweb = $web.webs.add("Test1", "Test1", "", 1033, "STS#0", $false, $false);
UploadFile $subweb
UploadFile $subweb
UploadFile $subweb
UploadFile $subweb
UploadFile $subweb

ReportRowCounts($cdb)

$subweb.delete()

ReportRowCounts($cdb)

You will see the AllDocStreams table continues to get larger and larger.  This is the table that has your BLOBS!  The worst table to have a database leak!  From a high level, what does this mean?  It means if you turn on versioning, and say upload a 1Gb file and then make 5 changes to it, you will have 5GB of storage used in your database.  If you then delete the web, you will lose file pointers in the database and that 5GB will remain in the database forever and never get cleaned up.  Now, how likely is it that you are creating and deleting webs in production?  Not too many people will have a fancy process setup like this, but in Development and QA, you will.  I can't afford to keep restorting a "clean" copy of my development databases everytime it gets too big.

NOTE:  This bug shows up in all builds after SP1 (the web recycle build), my environment is the latest release build of 14.6112.5000.

Here's how to determine if you are having a problem and how BIG it is:

$global:count = 0
$global:size = 0

function CheckDatabase($cdb)
{
$connString = $cdb.LegacyDatabaseConnectionString
$conn = new-object system.data.sqlclient.sqlconnection
$conn.connectionstring = $connstring
$conn.open()

$sql = "select count(*) as count, sum(datalength(content)) as size from alldocstreams where id not in (select id from alldocs)";
$cmd = new-object system.data.sqlclient.sqlcommand($sql, $conn)
$reader = $cmd.executereader()

while($reader.read())
{
$count = [double]::parse($reader["count"].tostring())
$size = [double]::parse($reader["size"].tostring())

}

$reader.close()
$conn.close()

$global:Count += $count
$global:size += $size

}

$cdbs = get-spcontentdatabase

foreach ($cdb in $cdbs)
{
CheckDatabase $cdb
}

"Orphaned rows: " + $global:count
"Orphaned rows size: " + $global:size + " bytes"

Microsoft…you need to get us a cumulative updatehot fix RIGHT NOW.

UPDATE:  AUGUST 2012 Cumulative Update fixes this bug:
http://technet.microsoft.com/en-us/sharepoint/ff800847.aspx

Not one to say enjoy too, but at least I know what is going on now and so do you!
Chris

Follow me on twitter: @givenscj

Check out the previous blog post:
https://blogs.architectingconnectedsystems.com/blogs/cjg/archive/2012/04/20/Project-Server-PSI-WCF-bug-_2D00_-WSEC_5F00_CAT_5F00_UID-and-WSEC_5F00_GRP_5F00_UID.aspx

The workflow failed to start due to an internal error

Yeah, that error.  Like an STD, its the one you hope you don't get! There are many reasons this error can creep up on you.  The most common being that the content types are corrupted and cannot be assigned to the task and history lists.

There are several blog posts that try to help here:

  • Uninstall and re-install the workflow features
    • In essense this should be the fall back, as it should remove the content types and put them back – as I found out, this didn't work in my case
  • If you are building your own workflow, ensure that your dlls have been loaded and the assembly manifests match up 
  • Make sure your Infopath forms are in the right places and haven't been modified
    • Typically, the forms are loaded up at the site collection under (_Catalogs/wfpub)
  • Make sure your web.config file was not corrupted and all the workflow entries exist (System.Workflow.ComponentModel.WorkflowCompiler)

So what was special in my case that none of these worked?  A simple answer, an orphaned web.  We were doing some migration work and we started to move a very large web from one web application to another.  We stopped the process halfway through, then we deleted the failed web.  Unfortunately, we didn't realize that this created the orphaned web.  As part of being orphaned, the transaction that does the deleting doesn't complete all its tasks and you are left with residual in the database. 

How did I reach this conclusion?  I tested workflows in another site collection in the same web application, they worked (ruling out that corruption occured via cumulative updates and feature corruption).  I tested the workflows in two different webs in the same site collection, both failed.  I tested an import on a different QA server and workflows still worked (but being that I didn't replicate what we did exactly last time, stop halfway, not a reliable test).  I kept at it and re-fired the workflow and saw that it would execute on the second or third execution, but it wouldn't create any tasks.  That lead me to believe that there was something wrong with the task list.  I looked at the working task list and saw that the content types DID exist on the list, but in the broken site, they did not.  I decided to manually add the content type via powershell and bingo…a helpful error ("Object reference not found").  Doing some searching I ran across this post:

http://social.technet.microsoft.com/Forums/zh/sharepoint2010programming/thread/dc211298-75b4-4c1a-8c95-acf6d610ed6f

Each content type has to have a field.  Looking at the content types, they didn't have any fields!  How weird right?  That made me realize that the content types were corrupt.  Therefore, I needed to delete all the content types and parents that didn't have fields.  This started at Publishing Approval Workflow Task (en-US)->SharePoint Server Workflow Task->Workflow Task.  Workflow task being one before the system content type "Task".  If you lose that one, you are screwed!

Luckily we didn't have many workflows so I decided to delete all the workflow content types (from all Task lists, which means the tasks must be deleted too).  I was able to delete the first two easily (turn off the features), but when I went to delete "Workflow Task" it would not delete as it was part of a feature (that meant chaning the bit column in the database for the content type)!  I turned off the feature (695b6570-a48b-4a8e-8ea5-26ea7fc1d162), but it still would not delete as it was being used!  So using the handly SPContentTypeUsage class (as blogged here – http://sharepoint.mindsharpblogs.com/NancyB/archive/2011/01/17/Finding-children-the-easy-way-(Content-Type-children,-that-is).aspx).  I was able to find the usage of the content type.  To my amazement…a deleted/orphaned web was showing. 

Once a web is deleted, you have no visibility to it via the object model.  That means a trip to the database tables was the next step.  Remember, the residual I mentioned earlier?   In our case, the ContentType and ContentTypeUsage tables had yuky residual in them.  I had to manually remove the ContentTypeUsage records, then manually delete the ContentType row for the orphaned web.

After that i was able to remove the ContentType via the object model.  I then reactived the workflow features and my problem was solved!  All the content types show fields for them now and all workflows work as expected!

Enjoy,
Chris