From 8588c0b300d441b51cf1deead13228ef97dbeaf4 Mon Sep 17 00:00:00 2001 From: Oliver Date: Mon, 10 Jun 2024 16:59:05 +0200 Subject: [PATCH] clean up pipeline scripts and allow usage of semantic versioning (#268) Update the process for creating versions: Update the Changelog Move all current changes to the [Released] section in the changelog. Determine the new version number based on semantic versioning and add the release date. Update the Version Configuration Use the new version number to update the current_version.cfg. Push Changes Push these changes to the branch you want to release from (main/develop/or your branch). Create a New Version Tag on GitHub Go to GitHub and create a new version tag on the branch. This tag should be the full version string, such as "0.3.0-1-aasV3-alpha-develop". The build number can be omitted in the tag name. --- .../workflows/build-and-package-release.yml | 59 +++++--------- .github/workflows/check-release.yml | 29 +++---- README.md | 36 +++++++++ src/BuildForRelease.ps1 | 51 +++++------- src/BuildVersionNumber.ps1 | 78 ++++++++++++++++++ src/PackageRelease.ps1 | 81 +------------------ src/UpdateProjectVersions.ps1 | 28 +++++++ 7 files changed, 201 insertions(+), 161 deletions(-) create mode 100644 src/BuildVersionNumber.ps1 create mode 100644 src/UpdateProjectVersions.ps1 diff --git a/.github/workflows/build-and-package-release.yml b/.github/workflows/build-and-package-release.yml index d3c31f9a2..0ffdefe2b 100644 --- a/.github/workflows/build-and-package-release.yml +++ b/.github/workflows/build-and-package-release.yml @@ -9,68 +9,51 @@ jobs: Build-and-package-release: runs-on: windows-latest steps: - - uses: actions/checkout@master + - uses: actions/checkout@v3 - - name: Infer the version from the github ref + - name: Infer the version from the GitHub ref id: inferVersion run: | - $prefix = "refs/tags/v" - if (!${env:GITHUB_REF}.StartsWith($prefix)) - { - throw "Unexpected GITHUB_REF: ${env:GITHUB_REF}" - } - - $version = ${env:GITHUB_REF}.Substring($prefix.Length) - Write-Host "The version is: $version" - - if ($version.Contains("'")) - { - throw "Unexpected version containing a single quote: $version" - } - if ($version.Contains('"')) - { - throw "Unexpected version containing a double quote: $version" - } - if ($version.Contains(':')) - { - throw "Unexpected version containing a full colon: $version" - } + $version = .\GetVersion.ps1 -suffix alpha + echo "::set-output name=version::$version" + shell: pwsh - Write-Output "::set-output name=version::$version" - - - name: Install .NET core - uses: actions/setup-dotnet@v1 + - name: Install .NET Core + uses: actions/setup-dotnet@v3 with: dotnet-version: '6.0.x' - - name: Build for the release + - name: Build for release + working-directory: src + run: .\BuildForRelease.ps1 + shell: pwsh + + - name: Update version numbers in project working-directory: src - run: powershell .\BuildForRelease.ps1 + run: .\UpdateProjectVersions.ps1 -version ${{ steps.inferVersion.outputs.version }} + shell: pwsh - name: Package the release working-directory: src run: | $version = '${{ steps.inferVersion.outputs.version }}' Write-Host "Packaging for the release version: $version" - powershell .\PackageRelease.ps1 -version $version + .\PackageRelease.ps1 -version $version + shell: pwsh - name: Rename the release assets - working-directory: ./ + working-directory: . run: | - Write-Host "Current working directory: $(Get-Location)" - $version = '${{ steps.inferVersion.outputs.version }}' $releaseDir = Join-Path $(Get-Location) "artefacts\release\$version" Write-Host "Release directory: $releaseDir" - if (!(Test-Path $releaseDir)) - { + if (!(Test-Path $releaseDir)) { throw "The release directory does not exist: $releaseDir" } $archives = Get-ChildItem $releaseDir -Filter *.zip - foreach($archive in $archives) - { + foreach($archive in $archives) { $path = $archive.FullName Write-Host "The path to the archive is: $path" @@ -78,10 +61,10 @@ jobs: Write-Host "The name without extension is: $nameWoExt" $target = Join-Path $releaseDir ($nameWoExt + "." + $version + ".zip") - Write-Host "Moving: $path -> $target" Move-Item -Path $path -Destination $target } + shell: pwsh - name: Upload the release assets uses: AButler/upload-release-assets@v2.0 diff --git a/.github/workflows/check-release.yml b/.github/workflows/check-release.yml index 01a00fa09..cddc7b2de 100644 --- a/.github/workflows/check-release.yml +++ b/.github/workflows/check-release.yml @@ -34,39 +34,40 @@ jobs: uses: actions/setup-dotnet@v3 with: dotnet-version: '6.0.x' - - # Builds the project for release by executing the BuildForRelease.ps1 PowerShell script in the 'src' directory. + + - name: Infer the version + id: inferVersion + run: | + $version = .\GetVersion.ps1 -suffix alpha + Write-Output "::set-output name=version::$version" + shell: pwsh + - name: Build for release description: working-directory: src run: .\BuildForRelease.ps1 shell: pwsh - - # Compares the output of the --help command with the README file to ensure consistency. + - name: Package working-directory: src - run: .\PackageRelease.ps1 + run: .\PackageRelease.ps1 -version ${{ steps.inferVersion.outputs.version }} shell: pwsh - with: - suffix: alpha - - # Uploads the AasxServerBlazor artifact with a timestamp to the artifacts' repository. + - name: Upload AasxServerBlazor uses: actions/upload-artifact@v3 with: - name: AasxServerBlazor.LATEST.alpha.${{ steps.setTimestamp.outputs.timestamp }} + name: AasxServerBlazor.LATEST.${{ steps.inferVersion.outputs.version }}.${{ steps.setTimestamp.outputs.timestamp }} path: artefacts/release/LATEST.alpha/AasxServerBlazor.zip - - # Uploads the AasxServerAspNetCore artifact with a timestamp to the artifacts' repository. + - name: Upload AasxServerAspNetCore uses: actions/upload-artifact@v3 with: - name: AasxServerAspNetCore.LATEST.alpha.${{ steps.setTimestamp.outputs.timestamp }} + name: AasxServerAspNetCore.LATEST.${{ steps.inferVersion.outputs.version }}.${{ steps.setTimestamp.outputs.timestamp }} path: artefacts/release/LATEST.alpha/AasxServerAspNetCore.zip # Uncomment the following steps if you need to upload the AasxServerWindows artifact # - name: Upload AasxServerWindows # uses: actions/upload-artifact@v3 # with: - # name: AasxServerWindows.LATEST.alpha.${{ steps.setTimestamp.outputs.timestamp }} + # name: AasxServerWindows.LATEST.${{ steps.inferVersion.outputs.version }}.${{ steps.setTimestamp.outputs.timestamp }} # path: artefacts/release/LATEST.alpha/AasxServerWindows.zip diff --git a/README.md b/README.md index 8d0c3f8d6..69ae2e288 100644 --- a/README.md +++ b/README.md @@ -114,6 +114,42 @@ An example GraphQL query is: If you want to create a registry and also automatically POST to it, please take a look at our [GitHub issues](https://github.com/admin-shell-io/aasx-server/issues/189) page. +## CREATE NEW RELEASES + +We've transitioned to [semantic versioning](https://semver.org) for better version distinctness. All versions follow this schema: + +``` +..---- +``` + +- **buildnumber**: An incremented value for each build, important for development or latest releases to distinguish builds even if there's no new version number. +- **AAS Schema Version**: Indicates the AAS main schema used in this version. +- **alpha**: Indicates this is still an alpha build, not a finished release. +- **stable**: The latest stable release, where the main features are confirmed working. +- **latest**: The most recent build on the main branch. It's relatively stable but may have some issues. +- **develop**: A build from a branch other than main or develop. It's for testing and may be unstable. + +### Release a New Version + +With the change to semantic versioning, the release process has been updated as well. + +To release a new version, follow these steps: + +1. **Update the Changelog** + - Move all current changes to the [Released] section in the [changelog](CHANGELOG.md). + - Determine the new version number based on semantic versioning and add the release date. +2. **Update the Version Configuration** + - Use the new version number to update the [current_version.cfg](src/current_version.cfg). +3. **Push Changes** + - Push these changes to the branch you want to release from (main/develop/or your branch). +4. **Create a New Version Tag on GitHub** + - Go to GitHub and create a new version tag on the branch. This tag should be the full version string, such as "0.3.0-1-aasV3-alpha-develop". The build number can be omitted in the tag name. + +### Example Version Tags +- `1.0.0-1-aasV3-alpha-develop`: An alpha build on a develop branch with build number 1. +- `1.0.0-2-aasV3-alpha-stable`: A stable release with build number 2. +- `1.0.0-3-aasV3-alpha-latest`: The latest build on the main branch with build number 3. + ## OLD DOCUMENTATION This documentation will be updated to V3 soon. diff --git a/src/BuildForRelease.ps1 b/src/BuildForRelease.ps1 index 44a55fef5..74167ca49 100644 --- a/src/BuildForRelease.ps1 +++ b/src/BuildForRelease.ps1 @@ -6,50 +6,47 @@ <# .DESCRIPTION -This script builds the solution for debugging (manual or automatic testing). +This script builds the solution for debugging (manual or automatic testing) or cleans up the previous build. #> # Set error action preference to stop on errors. $ErrorActionPreference = "Stop" +# Import necessary functions from the Common module. Import-Module (Join-Path $PSScriptRoot Common.psm1) -Function AssertDotnet, GetArtefactsDir -function CopyContentForDemo($Destination) -{ +function CopyContentForDemo($Destination) { $contentForDemoDir = Join-Path (Split-Path -Parent $PSScriptRoot) "content-for-demo" - if (!(Test-Path $contentForDemoDir)) - { + if (!(Test-Path $contentForDemoDir)) { throw "The directory with the content for demo does not exist: $contentForDemoDir" } Write-Host "Copying content for demo from $contentForDemoDir to: $Destination" - Get-ChildItem -Path $contentForDemoDir | Copy-Item -Destination $Destination -Recurse -Container -Force } -function Main -{ +function Main { # Change to the script root directory. Set-Location $PSScriptRoot # Define the base build directory. $baseBuildDir = Join-Path $(GetArtefactsDir) "build" | Join-Path -ChildPath "Release" - if ($clean) - { + if ($clean) { # Clean up previous build if requested. - Write-Host "dotnet clean'ing ..." + Write-Host "Cleaning up previous build..." dotnet clean - if ($LASTEXITCODE -ne 0) - { - throw "Failed to dotnet clean." + if ($LASTEXITCODE -ne 0) { + throw "Failed to clean the project." } Write-Host "Removing the build directory: $baseBuildDir" - Remove-Item -LiteralPath $baseBuildDir -Force -Recurse - } - else - { + if (Test-Path $baseBuildDir) { + Remove-Item -LiteralPath $baseBuildDir -Force -Recurse + } else { + Write-Host "Build directory does not exist: $baseBuildDir" + } + } else { # Ensure dotnet is installed. AssertDotnet @@ -59,16 +56,13 @@ function Main "AasxServerAspNetCore" ) - foreach ($target in $dotnetTargets) - { + foreach ($target in $dotnetTargets) { $buildDir = Join-Path $baseBuildDir $target - Write-Host "Publishing with dotnet $target to: $buildDir" - + Write-Host "Publishing $target to: $buildDir" dotnet publish -c Release -o $buildDir $target - if ($LASTEXITCODE -ne 0) - { - throw "Failed to dotnet publish: $target" + if ($LASTEXITCODE -ne 0) { + throw "Failed to publish the project: $target" } # Copy content for demo to the build directory. @@ -79,11 +73,8 @@ function Main # Store the current location, execute the main function, and return to the original location. $previousLocation = Get-Location -try -{ +try { Main -} -finally -{ +} finally { Set-Location $previousLocation } diff --git a/src/BuildVersionNumber.ps1 b/src/BuildVersionNumber.ps1 new file mode 100644 index 000000000..0dca51903 --- /dev/null +++ b/src/BuildVersionNumber.ps1 @@ -0,0 +1,78 @@ +param( + [Parameter(HelpMessage = "Suffix to be appended to the version (e.g., alpha, beta)", Mandatory = $false)] + [string] + $suffix = "alpha" +) + +# Set error action preference to stop on errors. +$ErrorActionPreference = "Stop" + +function GetNextBuildNumber +{ + # Read the current build number from the file. + $currentBuild = Get-Content (Join-Path $PSScriptRoot "current_build_number.cfg") | ForEach-Object { $_.Trim() } + + # Increment the build number and save it back to the file. + $nextBuild = [int]$currentBuild + 1 + $nextBuild | Set-Content (Join-Path $PSScriptRoot "current_build_number.cfg") + + # Return the incremented build number. + return $nextBuild +} + +function GetVersionCore +{ + # Read the current version from the file. + $versionCore = Get-Content (Join-Path $PSScriptRoot "current_version.cfg") | ForEach-Object { $_.Trim() } + + # Return the version core. + return $versionCore +} + +function GetBuildSuffix +{ + # Determine if the build is on the main or release branch. + $branch = git branch --show-current 2> $null # Suppress errors if not in a Git repository + if (-not $?) + { + Write-Host "Not in a Git repository. Assuming develop branch." + return "develop" + } + + if ($branch -eq "main") + { + return "latest" + } + elseif ($branch -eq "release") + { + return "stable" + } + else + { + Write-Host "Not main or release branch. Assuming develop branch." + return "develop" + } +} + +function GetVersion +{ + # Get the version core from the file. + $versionCore = GetVersionCore + + # Get the build suffix based on the branch. + $buildSuffix = GetBuildSuffix + + # Get the next build number. + $buildNumber = GetNextBuildNumber + + $aasmodel = "aasV3" + + # Construct the semantic version. + $semanticVersion = "$versionCore-$buildNumber-$aasmodel-$suffix-$buildSuffix" + + return $semanticVersion +} + +# Generate the version and print it to output. +$version = GetVersion +Write-Output $version diff --git a/src/PackageRelease.ps1 b/src/PackageRelease.ps1 index 0a112e465..286bfc56b 100644 --- a/src/PackageRelease.ps1 +++ b/src/PackageRelease.ps1 @@ -1,7 +1,7 @@ param( - [Parameter(HelpMessage = "Suffix to be appended to the version (e.g., alpha, beta)", Mandatory = $false)] + [Parameter(HelpMessage = "Suffix to be appended to the version (e.g., alpha, beta)", Mandatory = $true)] [string] - $suffix = "alpha" + $version = "0.3.0" ) # Set error action preference to stop on errors. @@ -10,77 +10,6 @@ $ErrorActionPreference = "Stop" # Import necessary functions from Common.psm1 module. Import-Module (Join-Path $PSScriptRoot Common.psm1) -Function GetArtefactsDir -function GetNextBuildNumber { - # Read the current build number from the file. - $currentBuild = Get-Content (Join-Path $PSScriptRoot "current_build_number.cfg") | ForEach-Object { $_.Trim() } - - # Increment the build number and save it back to the file. - $nextBuild = [int]$currentBuild + 1 - $nextBuild | Set-Content (Join-Path $PSScriptRoot "current_build_number.cfg") - - # Return the incremented build number. - return $nextBuild -} - -function GetVersionCore { - # Read the current version from the file. - $versionCore = Get-Content (Join-Path $PSScriptRoot "current_version.cfg") | ForEach-Object { $_.Trim() } - - # Return the version core. - return $versionCore -} - -function GetBuildSuffix { - # Determine if the build is on the main or release branch. - $branch = git branch --show-current 2>$null # Suppress errors if not in a Git repository - if (-not $?) { - Write-Host "Not in a Git repository. Assuming develop branch." - return "develop" - } - - if ($branch -eq "main") { - return "latest" - } - elseif ($branch -eq "release") { - return "stable" - } - else { - Write-Host "Not main or release branch. Assuming develop branch." - return "develop" - } -} - -function GetVersion { - # Get the version core from the file. - $versionCore = GetVersionCore - - # Get the build suffix based on the branch. - $buildSuffix = GetBuildSuffix - - # Get the next build number. - $buildNumber = GetNextBuildNumber - - $aasmodel = "aasV3" - - # Construct the semantic version. - $semanticVersion = "$versionCore-$buildNumber-$aasmodel-$suffix-$buildSuffix" - - return $semanticVersion -} - -function UpdateProjectVersions($version) { - # Get all csproj files in the solution. - $projectFiles = Get-ChildItem -Path "$PSScriptRoot\.." -Recurse -Filter *.csproj - - # Iterate through each project file and update the tag. - foreach ($file in $projectFiles) { - Write-Host "Updating version in $($file.FullName)" - (Get-Content -Path $file.FullName) | ForEach-Object { - $_ -replace '.*<\/Version>', "$version" - } | Set-Content -Path $file.FullName - } -} - function PackageRelease($outputDir, $version) { # Define the base directory where built release files are stored. $baseBuildDir = Join-Path $(GetArtefactsDir) "build" | Join-Path -ChildPath "Release" @@ -118,17 +47,11 @@ function PackageRelease($outputDir, $version) { } function Main { - # Get the semantic version. - $version = GetVersion - # Validate the generated semantic version. if ($version -eq "") { throw "Failed to generate semantic version." } - # Update project versions. - UpdateProjectVersions $version - # Define the output directory for the packaged release. $outputDir = Join-Path $(GetArtefactsDir) "release" | Join-Path -ChildPath $version diff --git a/src/UpdateProjectVersions.ps1 b/src/UpdateProjectVersions.ps1 new file mode 100644 index 000000000..7d22edfb2 --- /dev/null +++ b/src/UpdateProjectVersions.ps1 @@ -0,0 +1,28 @@ +param( + [Parameter(HelpMessage = "Version to be updated in the project files", Mandatory = $true)] + [string] + $version +) + +# Set error action preference to stop on errors. +$ErrorActionPreference = "Stop" + +function UpdateProjectVersions { + param ( + [string]$version + ) + + # Get all csproj files in the solution. + $projectFiles = Get-ChildItem -Path "$PSScriptRoot\.." -Recurse -Filter *.csproj + + # Iterate through each project file and update the tag. + foreach ($file in $projectFiles) { + Write-Host "Updating version in $($file.FullName)" + (Get-Content -Path $file.FullName) | ForEach-Object { + $_ -replace '.*<\/Version>', "$version" + } | Set-Content -Path $file.FullName + } +} + +# Execute the function +UpdateProjectVersions -version $version