microsoft/healthcare-shared-components
Publicmirrored fromhttps://github.com/microsoft/healthcare-shared-componentsAvailable
scripts/Publish-LocalChanges.ps1
161lines · modecode
| 1 | <# |
| 2 | .SYNOPSIS |
| 3 | Packs the local component changes, publishes to the local NuGet feed, and updates all of the project references under $RootPath. |
| 4 | |
| 5 | .PARAMETER RootPath |
| 6 | The root path where to look for projects to be replaced. If not specified, then the current path will be used. |
| 7 | |
| 8 | .PARAMETER DoNotUpdateProjectReferences |
| 9 | A flag indicating to not update the project reference. |
| 10 | |
| 11 | .PARAMETER SkipBuild |
| 12 | A flag indicating to skip building. |
| 13 | #> |
| 14 | |
| 15 | param( |
| 16 | [string]$RootPath, |
| 17 | |
| 18 | [switch]$DoNotUpdateProjectReferences, |
| 19 | |
| 20 | [switch]$SkipBuild |
| 21 | ) |
| 22 | |
| 23 | Set-StrictMode -Version Latest |
| 24 | $ErrorActionPreference = "stop" |
| 25 | $Global:InformationPreference = "continue" |
| 26 | |
| 27 | Set-Variable RepoRootPath -Option Constant -Value (Resolve-Path "$PSScriptRoot\..") |
| 28 | Set-Variable LocalNuGetFeedPath -Option Constant -Value "$RepoRootPath\.nuget-local" |
| 29 | |
| 30 | function ConfigureLocalNuGetFeed() { |
| 31 | # Add the local NuGet feed to nuget.config if needed. |
| 32 | $nugetConfigFileName = "$RootPath\nuget.config" |
| 33 | $nugetConfig = [xml](Get-Content $nugetConfigFileName) |
| 34 | |
| 35 | $localFeed = $nugetConfig.configuration.packageSources.add | Where-Object { $_.value -eq $LocalNuGetFeedPath } |
| 36 | |
| 37 | if ($localFeed -eq $null) { |
| 38 | # Add the local NuGet feed |
| 39 | $element = $nugetConfig.CreateElement("add") |
| 40 | |
| 41 | $keyAttribute = $nugetConfig.CreateAttribute("key") |
| 42 | $keyAttribute.Value = "Local NuGet Feed" |
| 43 | |
| 44 | $valueAttribute = $nugetConfig.CreateAttribute("value") |
| 45 | $valueAttribute.Value = $LocalNuGetFeedPath |
| 46 | |
| 47 | $element.Attributes.Append($keyAttribute) | Out-Null |
| 48 | $element.Attributes.Append($valueAttribute) | Out-Null |
| 49 | |
| 50 | $nugetConfig.configuration.packageSources.AppendChild($element) |
| 51 | |
| 52 | $nugetConfig.Save($nugetConfigFileName) |
| 53 | } |
| 54 | } |
| 55 | |
| 56 | function CheckUnstagedProjects($ProjectsWithDependencies) { |
| 57 | # Check to see if any of the projects already has pending changes. |
| 58 | $listOfUnstagedFiles = &git diff --name-only | ForEach-Object { Resolve-Path $_ -ErrorAction SilentlyContinue } |
| 59 | |
| 60 | $projectsWithPendingChange = $listOfUnstagedFiles | Where-Object { $_ -in $ProjectsWithDependencies } |
| 61 | |
| 62 | if ($projectsWithPendingChange) { |
| 63 | $projects = [string]::Join("`n", $projectsWithPendingChange); |
| 64 | |
| 65 | $title = "Confirm" |
| 66 | $prompt = "The following projects has pending change:`n`n$projects`n`nSelect Yes to continue with update or No to abort." |
| 67 | $continue = New-Object System.Management.Automation.Host.ChoiceDescription '&Yes', 'Continue the operation' |
| 68 | $abort = New-Object System.Management.Automation.Host.ChoiceDescription '&No', "Abort the operation" |
| 69 | |
| 70 | $choice = $host.UI.PromptForChoice($title, $prompt, @($continue, $abort), 0) |
| 71 | |
| 72 | if ($choice -eq 1) { |
| 73 | exit |
| 74 | } |
| 75 | } |
| 76 | } |
| 77 | |
| 78 | if ([string]::IsNullOrEmpty($RootPath)) { |
| 79 | $RootPath = Get-Location |
| 80 | } |
| 81 | |
| 82 | if (!(Test-Path $RootPath)) { |
| 83 | Write-Error "The root path could not be found. Please make sure the specified path is correct." |
| 84 | exit |
| 85 | } |
| 86 | |
| 87 | # Generate the version suffix using the branch name of the current time. |
| 88 | Push-Location $RepoRootPath |
| 89 | |
| 90 | try { |
| 91 | $branchName = &git rev-parse --abbrev-ref HEAD |
| 92 | $branchNameParts = $branchName.Replace('#', '').Split("/") |
| 93 | $version = "1.0.0-$($branchNameParts[$branchNameParts.Length - 1])-$(Get-Date -Format yyyyMMdd-HHmmss)-preview" |
| 94 | |
| 95 | # Find all projects in the components. |
| 96 | $projects = Get-ChildItem -Recurse -Include *.csproj -Exclude *Tests.csproj $RepoRootPath |
| 97 | |
| 98 | # Create NuGet package for each of the projects. |
| 99 | $tempPath = [IO.Path]::Combine([IO.Path]::GetTempPath(), [Guid]::NewGuid()) |
| 100 | |
| 101 | $projects | ForEach-Object { |
| 102 | if ($SkipBuild) { |
| 103 | &dotnet pack -o $tempPath --no-build --include-symbols $_.FullName /p:PackageVersion=$version |
| 104 | } |
| 105 | else { |
| 106 | &dotnet pack -o $tempPath --include-symbols $_.FullName /p:PackageVersion=$version |
| 107 | } |
| 108 | } |
| 109 | |
| 110 | # Publish to local NuGet feed. |
| 111 | if (!(Test-Path $LocalNuGetFeedPath)) { |
| 112 | New-Item $LocalNuGetFeedPath -ItemType Directory | Out-Null |
| 113 | } |
| 114 | |
| 115 | Get-ChildItem -Recurse -Include *.symbols.nupkg $tempPath | ForEach-Object { |
| 116 | &dotnet nuget push $_.FullName -s $LocalNuGetFeedPath |
| 117 | } |
| 118 | |
| 119 | # Delete the temp |
| 120 | Remove-Item -Path $tempPath -Recurse |
| 121 | } finally { |
| 122 | Pop-Location |
| 123 | } |
| 124 | |
| 125 | # Update the project references |
| 126 | Push-Location $RootPath |
| 127 | |
| 128 | try { |
| 129 | ConfigureLocalNuGetFeed |
| 130 | |
| 131 | if (!$DoNotUpdateProjectReferences) { |
| 132 | # Find all projects that has dependencies on these components. |
| 133 | $projectsWithDependencies = (Get-ChildItem -Recurse -Include *.csproj $RootPath).FullName |
| 134 | |
| 135 | CheckUnstagedProjects($projectsWithDependencies) |
| 136 | |
| 137 | $utf8WithBom = New-Object System.Text.UTF8Encoding($true) |
| 138 | |
| 139 | $projectsWithDependencies | ForEach-Object { |
| 140 | Write-Information "Updating $_" |
| 141 | |
| 142 | $project = [xml](Get-Content $_) |
| 143 | |
| 144 | $project.SelectNodes("Project/ItemGroup/PackageReference") | |
| 145 | Where-Object { $_.Include -match "Microsoft.Health.*" } | |
| 146 | ForEach-Object { $_.Version = $version } |
| 147 | |
| 148 | $writer = New-Object System.IO.StreamWriter($_, $false, $utf8WithBom) |
| 149 | |
| 150 | $project.Save($writer) |
| 151 | |
| 152 | $writer.Close() |
| 153 | |
| 154 | # Removed the XML declaration. |
| 155 | $project = Get-Content $_ |
| 156 | $project | Select-Object -Skip 1 | Set-Content -Encoding UTF8 -Path $_ |
| 157 | } |
| 158 | } |
| 159 | } finally { |
| 160 | Pop-Location |
| 161 | } |
| 162 | |