简体   繁体   中英

SharePoint 2010 handle solution update

Let's say I have an SP2010 solution which does many things: create content types, instantiate lists, add event receivers, webs, the whole bunch. Now let's say I develop new stuff: change some content types, change some event receivers, etc. Existing lists won't be affected by any of those. It's a given I guess, but I need to apply the changes everywhere. How would you handle solution updating nicely?

I know SharePoint has an upgrade framework (see SPPersistedUpgradableObject.NeedsUpgrade), but I think it applies to upgrades of the SharePoint product itself.

So what to do? Store the current version number in a property bag somewhere, hook up a feature activated event receiver, recurse through the whole world (webapps, sites, webs, lists...) and upgrade everything? There must be some framework to help me with this, if nothing else, then at least a progress bar should be shown somewhere because it could take like 5 minutes or more. All ideas welcome.

Here is how I do it:

Before deploying my updated feature, I open the feature in Visual Studio and change the Version property (when I create new features, I set the version to 1.0.0.0). Next, I click the Manifest button, expand the Edit Options section, and enter UpgradeActions data.

The following is a slightly modified version of one my upgraded features:

<?xml version="1.0" encoding="utf-8" ?>
<Feature xmlns="http://schemas.microsoft.com/sharepoint/">
 <UpgradeActions>
  <VersionRange BeginVersion="1.0.0.0" EndVersion="1.1.0.0">
   <CustomUpgradeAction Name="UpgradeTo1v1" />
  </VersionRange>
  <VersionRange BeginVersion="1.1.0.0" EndVersion="1.3.0.0">
   <CustomUpgradeAction Name="UpgradeTo1v3" />
  </VersionRange>
  <VersionRange BeginVersion="1.3.0.0" EndVersion="1.4.0.0">
   <CustomUpgradeAction Name="UpgradeTo1v4">
    <Parameters>
     <Parameter Name="OptionalParameter">Values go here</Parameter>
    </Parameters>
   </CustomUpgradeAction>
  </VersionRange>
 </UpgradeActions>
</Feature>

I then add or modify the FeatureUpgrading method of my feature receiver:

[SharePointPermission(SecurityAction.LinkDemand, ObjectModel = true)]
public override void FeatureUpgrading(
    SPFeatureReceiverProperties properties, 
    string upgradeActionName, 
    System.Collections.Generic.IDictionary<string, string> parameters)
{
    SPSite site = properties.Feature.Parent as SPSite;
    SPWeb web = site.RootWeb;
    switch (upgradeActionName)
    {
        case "UpgradeTo1v1":
            UpgradeTo1v1(site, properties, parameters);
            break;
        case "UpgradeTo1v3":
            UpgradeTo1v3(site, properties, parameters);
            break;
        case "UpgradeTo1v4":
            UpgradeTo1v4(site, properties, parameters);
            break;
    }
}

My private upgrade methods make any changes programmatically that are not achieved automatically when the updated solution package is deployed. I deploy the solution package using the following PowerShell script:

Write-Host "Upgrading solution: $SolutionPackageName" -NoNewline
Update-SPSolution -Identity $SolutionPackageName -LiteralPath $SolutionPackagePath -GACDeployment -Confirm:$false -Force
while ($Solution.JobExists)
{
    Start-Sleep -s 2
}
Write-Host " - Done."

if ($UpdateFeatureGuids -ne $null)
{
    foreach ($site in Get-SPSite -Limit All) 
    {
        $UpdateFeatureGuids | % { $site.QueryFeatures([Guid]$_, [bool]$true) } | % { 
            $definitionId = $_.DefinitionId
            $parentUrl = $_.Parent.Url
            Write-Host "Upgrading feature: $definitionId $parentUrl"
            $_.Upgrade([bool]$false) | % { 
                if ($_ -ne $null)
                {
                    Format-List -InputObject $_ -Property Message, InnerException -Force 
                }
            }
            Write-Host "Upgrading feature: $definitionId $parentUrl - Done."
        }
        $site.Dispose()
    }
}

I really wish Update-SPSolution had a flag that let you upgrade all active features. I have yet to have a case where I've needed to update a feature but didn't want the programmatic upgrades to apply. So the rest of the PowerShell code does that for me by going through all site collections, finding all features in need of upgrade based on a predefined list, and then upgrading the feature on each site while displaying any errors that occur.

Note that Update-SPSolution only refreshes existing files. If you have added new files to your solution package, they will be ignored and will not be deployed. I would hope that the version history and upgrade-ability of a feature would not be nullified by a retract/deploy, but I have never tried it. Usually, if I need to add new files, I will create a new solution package.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM