Friday, October 15, 2010

SharePoint Content DB Restores

I know there are already a ton of articles, posts, etc. out there about this, but I have yet to find one that addresses all of these situations at once. In helping to administrate a SharePoint farm with 1000+ sites in well over 50+ site collections, I have had the opportunity to mop up after a few bone-headed blunders. Things had been quiet for some time and then I got a request to restore an excel file from 6 months ago. Turns out the library it was in did not have versioning turned on.

I was fairly sure on what I needed to do, but a little fuzzy on the exact procedures. "No problem", I said to myself, "I'll just pull up the documentation from the last time I did this." Oops! Apparently I did not document it last time, or I forgot where I put it, 'cause I couldn't find it anywhere. So this time around I made documentation and figured I would share it with the rest of the world. I'm sure there are other ways to do this, but I went for easy to follow, rather than sophisticated. Enjoy!

Restoring SharePoint Site or Item from Content Database Backup


  • If an entire site collection is not to be restored, then the content database must be restored to a staging farm.
  • The staging farm must be the same version/build as the production farm.
  • Any features (.wsp) that are active for the site in question on the production farm must be installed on the staging farm.


Restoring a site collection

To restore from a current version/build content db

  1. Stop the IIS website of the site collection to restore.
  2. Using SQL Server, set the content database for the site collection into single user mode.
  3. Restore the content db according to SQL Server db restore practices.
  4. Restart the IIS website.

To restore from a previous version/build content db

  1. Stop the IIS website of the site collection to restore.
  2. Using SharePoint Central Administration remove the content db of the site collection to be restored.
  3. Using SQL Server, set the content database for the site collection into single user mode.
  4. Restore the content db according to SQL Server db restore practices.
  5. Use the stsadm –o addcontentdb command to add the content database to the site collection (stsadm –o addcontentdb –url  -databasename ). Other options may be needed.
  6. Restart the IIS website.

** Please note that it is not required to start and stop the IIS site, but in some cases it is more user-friendly.

Restoring a web (sub web)
  1. Create an empty site collection on the staging farm (this can be a root or a sub site collection)
    • Sub site collections are a little more tricky and may be best created via the stsadm –o createsiteinnewdb command.
  2. Restore the content db according to SQL Server db restore practices.
  3. Using SharePoint Central Administration or stsadm, take the current content db for the site collection offline, or remove it.
  4. Use the stsadm –o addcontentdb command to add the content database to the site collection (stsadm –o addcontentdb –url -databasename ). Other options may be needed.
  5. Use the stsadm –o export and stsadm –o import commands to export the specific sub web from the staging farm and import it into a specified location on the production farm.
    • It may be beneficial to use various options from the export and import commands to preserve security, etc.
Restoring an item
  1. Create an empty site collection on the staging farm (this can be a root or a sub site collection)
    • Sub site collections are a little more tricky and may be best created via the stsadm –o createsiteinnewdb command.
  2. Restore the content db according to SQL Server db restore practices.
  3. Using SharePoint Central Administration or stsadm, take the current content db for the site collection offline, or remove it.
  4. Use the stsadm –o addcontentdb command to add the content database to the site collection (stsadm –o addcontentdb –url -databasename ). Other options may be needed.
  5. Find the item in question and move it to the production farm by whatever action(s) seem prudent.

Off the Market!

First of all, my apologies for not posting in some time. The tail end of the summer got quite busy for me, and although I was inspired to post some stuff here and there, alas, I did not. I do have a good reason however... I got married in September (destination wedding) and had a reception back home in early October.

As any good man knows, during the time approaching these events, I was at my bride's beck and call to help make sure things went as planned, and to help shoulder some of the stress involved with planning, etc. Now that we are through everything life seems simpler and we again have free time to take-up extra curriculars again. So the posting is back on!

Tuesday, July 27, 2010

Sitefinity Users Beware!

Okay so this is for anyone out there who plans on or is trying to run Telerik's Sitefinity <= 3.7 on IIS 7.0. If you haven't had much opportunity to read up on or play with IIS 7.0, then you may find this helpful. IIS 7.0 has changed the way that it processes IIS and ASP.NET reqests. In the past it would use separate pipelines for the 2 different types of requests, but now they are integrated into the same pipeline, which can allow for some powerful things to happen for applications that are written to take advantage of it. However for those applications that are not written to take advantage of it, frustration and confusion can ensue. This is where Sitefinity comes in...

Based on my own personal experience, if you are not careful IIS 7.0 will be set up with the DefaultAppPool, which uses the integrated request pipeline. Sitefinity will install and work, kinda, but you will get wierd 404 errors, which will drive you bonkers. Fortunately, there is a way around this by implementing an application pool that uses the classic request pipeline. If you make sure to install IIS 7.0 with IIS Metabase and IIS 6 configuration compatibility, there will be a 2nd application pool titled Classic .NET AppPool, which uses the classic request pipeline.

Simply switching the application to use this app pool will clear up a lot of gray and allow you to steer around any other issues you may have (most likely dealing with authentication). One other thing you may want to ensure is that the Classic .NET AppPool runs under the LocalSystem account. I believe that Telerik does have some additional documentation here, but I didn't find that until after I figure stuff out for myself. Go figure...

Monday, July 19, 2010

MS Forefront Identity Manager 2010

So I was asked by my boss to take a look at a MS Virtual Lab for Forefront Identity Manager (FIM) 2010, MS latest and greatest in the series of Identity lifecyle management tools. The lab essentially consisted of 3 sections, one dealing with account creation and provisioning, another dealing with self-service, approval-style group management, and another using a password reset utility to show off workflow capabilities. I must admit, that I did approach this lab with a bit of skepticism and contempt as I have already developed a web-based application for creating and provisioning accounts and have a hard time seeing the value in spending thousands of dollars on something that we basically already have and give up the ability to change/customize it. Anyway, this is my analysis and takeaway on what I have experienced.

The FIM interface is basically a web interface... and a poky one at that, unless that is just the virtual lab slowing everything down, but it did seem relatively intuitive, which is not surprising since MS has been at this for awhile now.

Section 1: Account Creation and Provisioning
The first section of the lab dealt with basic account creation and provisioning. Not very impressive, as what we already have does more in some areas and in areas that are lacking, could easily accomplish or exceed with a few minor modifications. The lab basically had you fill out a form with all of the particular account details, leaving room for data entry errors, etc and based on certain options selected from a dropdown list or two, automatically adds the user to a group or set of groups. All of this data apparently goes into a database backing the FIM somewhere, because the lab then has you fire up a script, which runs every 30 seconds, to synchronize the FIM with Active Directory. Two questions, why not interface directly with AD and second, why wait so long to synchronize. The issue I see with this is that there is no immediate feedback of success, and this could ultimately slow down the account creation process in a high demand environment. The application we have interfaces directly with AD as well as global account list and provides direct feedback of success/failure, as well as logging all of the attributes that have been set during the account creation process. As far as adding the account to specific groups based on options selected from dropdown lists, that framework essentially already exists, is easily extensible, and just needs to be implemented.

The other question that comes to mind is security trimming and customization. Sure it is nice to have a neat web interface that can be used to create accounts, but is the interface security trimmed or can it be? The current application is and the security trimming that exists can be extended and modified. What about customizations? The environment that exists does not lend itself well to working with FIM out of the box. The advantage to the current application is that it is built around the unique account creation/provisioning process, as well as other needs with regard to modifications, moves, and deletions, and because of this, is more agile with respect to modifications dictated by the process, instead of modifying the process to deal with inflexibility in the app.

Section 2: Self-Service Group Management
I have to admit this concept is pretty cool, and I do like the approach that MS has taken here as far as patterning goes. Basically, an AD group is created and ownership is given to a manager. It appears as though FIM serves as a broker or gatekeeper for the group membership. Somehow through the process of setting this up, an add-in is created for MS outlook whereby users, can apply to be members of a group. When a user applies for membership, a message is sent to the group owner and they can approve or deny, which in turns informs the original requester.

So this is a pretty neat process. However, I find a bit of a problem in the implementation of the process via an Outlook add-in. The add-in may only be specific to Outlook 2007+, which is not consistent in the environment, and it seems that it will more than likely require user training. Windows SharePoint Services (WSS) allows an option for requesting access to SharePoint groups, which basically uses the same workflow process, but it is web-based.

Other questions I have about this feature that FIM implements revolves around the groups themselves. Are the end users limited to which groups they can even see to apply to? I'm thinking about role-based access control (RBAC) here... There could be a whole list of groups that one set of people could apply for membership to that would be superfluous to another group of people. The current application that we have does not offer this capability, but certainly could, and it could do it while keeping RBAC trimming in mind as well. So although FIM offers a cool feature here, it is not something that is beyond the reach of extending the current application and doing it in a much easier to use web-based user portal that could exert some RBAC trimming.

Section 3: Password Reset Utility
Okay, so when I saw this in the lab outline my first though was "oh please... this is already being done", then I got into it... The lab assumes that the user forgets their password at the login screen and needs to reset it. The utility works essentially the same as any other password reset utility that you encounter on the web for any secure site, but most like banking sites. The lab first walks through the process of the user setting up the utility by picking specific questions and providing answers. It then walks you through as an admin to view the workflow that is actually associated with, or generates the utility program. Finally we log out of the system and run the utility from the log in prompt. Very cool! The user is able to reset their own password without any request for intervention. This could be a handy tool.

The current application does not have this exact feature, and even though it could easily enough, if there is not a way to place a link or call to the reset utility on the welcome/logon screen, it is a mute point. The only question/issue I have with this again goes back to software requirements. Is this something that can be done on WinXP or is it strictly Vista+.

Overall, my impressions from this lab left me with more questions than an feeling to be drawn to FIM 2010. However it did give me some cool ideas that I feel could easily be implemented in the web-based application that we currently use. The only thing that I do not think could be possible is a password reset from the welcome screen, and this is just because I'm not familiar with the possible hooks from that part of the OS. A systems engineer may be able to help shed light on this. However with the licensing cost that I have found for FIM 2010 @ $15,000 per server and $18 per CAL, I wonder if a password reset utility is worth that when the rest can be done in the current web application at a fraction of the cost, while remaining flexible to the demands of business processes.

Wednesday, June 30, 2010

Sys.InvalidOperationException: Could not find Updatepanel... blah, blah, blah

Okay, okay so I know every other developer that has a blog probably has one of these articles too, but I figured I'd throw my 2 cents in also and report on my specific encounter with this issue/situation. This was happening to me on a page where I had a dynamically visible insert form with a gridview displaying data. The insert form was inside of an update panel, and the gridview was not. The gridview had a couple of custom columns where I was doing some neato-fancy stuff. One such column was using a couple update panels for an embeded datalist from a related table and a popup calendar extender. Anyway upon clicking the insert button, I would get the whole "...Could not find Updatepanel..." error message. although the data would insert and the gridview would update just fine.

Now, of course the rest of the error message went on to read, "...if it is being updated dynamically then it must be inside another updatepanel...". Yeah, right, like that'll fix it! Me being the skeptical developer that I am, from the heady days of C/C++ on UNIX/AIX and the messages you would receive from that, I wasn't about to put alot of stock in an error message, let alone one from Microsoft. However, I figured I'd give it a try and dropped my gridview into an update panel. Well, whadayaknow, the error message disappeared and everything is now operating smoothly. So kudos to Microsoft for coming up with an error message that acutally helped to resolve the issue this time. Hopefully, this helps someone else who runs into something similar, or at least gets a couple laughs.

Thursday, June 17, 2010

Fun with Heterogeneous Environments

Okay, so I did some work for a client the other day. Nothing really big, just trying to help an MS Access app I developed for them years ago limp along through it's final days/months... who knows. Anyway, some background...

This app was developed back in 2002 or 2003, can't remember anymore and at the time it was developed, the client's machines consisted of a couple different flavors of windows and Office 2000. So naturally, the app was scoped and developed in Access 2000, which was pretty cool because with ART 2000  it could even run on machines that didn't have Office installed. The app is a basic split db with and MDE front end. As they began to use the application, requests for changes in functionality and schema came and went, and things went along swimingly.

Then one day, I get a call reporting that the application does not work on a certain user's computer. When I get on site I find that the environment had changed. This particular user had the latest and greatest OS and version of Office. Suprise!! My install package would no longer work. So I fixed the install and recommended and provided a bid to convert the app into a ASP.NET intranet app. Much more flexible, easier to update, no fuss, no muss... They were not interested, and wanted to leave things the way they were, as they were moving to a new product that was an ASP.NET web app (and more spendy than my bid mind you).


So I get a call a few months ago reporting that the client is upgrading to a new file server and would like to move the DB backend, but the front end code was throwing a bug that wouldn't allow it without a lot of complaining. I know, I know... bad developer! BAD!! I apologize for having the short-sightedness that this app would have such a long lifespan.

The request was to get rid of the errors and make it easy for the end users to relink the front end to the backend if it were ever moved again. No problem, that was the easy part. The hard part, was getting an install that would recognize and install the app on mulitple environmental flavors of OS & Office combos -- mmm... combos...  ---- Where was I?? Oh, yeah, so I did my reasearch and got my list of flavors and tried to come up with an install that would do the job w/o my having to sink a bunch of time into it. Got that to a point where I felt fairly good about, so I crossed my fingers and lined up the upgrade.

Upgrade day came and things started out not too bad, but 2 years had passed since the last time I had been out there and things changed quite a bit. Now I know what you're thinking... "My it must have been a pleasant, orderly suprise"... Wrong! It was actually a little worse than what my research had turned up. Multiple versions of Window (XP, Vista, 7) with multiple versions of Office (2k, XP, 2K3, 2K7). As if that was not bad enough, there were a few users who actually changed their drive letter assignments (i.e. C:\ was no longer the system drive). All considered, everything went fairly well, except for the machines with the wierd drive letter assignments.

I will attribute success to two things, using a batch file to open the font end using the generic MSACCESS.EXE <FILE_NAME> command line option ( and the nuggut of gold that I like to call Access 2000 Runtime. That's right Microsoft may have discontinued it but, ART 2k is awesome and can often save you in a pinch! In the end, with the smoke clearing, the client is happy with a version of the app that they can move around as they see fit so it can be used for historical purposes, and although I may not have anything to do with this app again I'm sure they will contact me other special projects as they come along. Who knows maybe this thing will go another 8 years?!!

Tuesday, June 15, 2010

The Beginning of Something Beautiful... or Truely Horrible!

Well, here it is, my first trepidacious steps into the world of the web log (or blog for you hip types). I can't promise much, other than the fact that I will try to post as often as possible when relevant information is needed for the masses. My hope is to keep the focus within the IT realm and report on things I have come across and how I solved them. However, do not be suprised, dear reader, if you stumble across an entry or two about iron horses or the occasional pan fryer. Why? Well, let's just say I like to keep you guessing. Thanks for reading, and hope to see you again soon!