Skip to content

Commit

Permalink
(chocolatey-community#32) Add InvokeBuild script and rename to Chocol…
Browse files Browse the repository at this point in the history
…atey-AU
  • Loading branch information
corbob committed Mar 5, 2024
1 parent 62e4670 commit 27cb8d9
Show file tree
Hide file tree
Showing 17 changed files with 646 additions and 128 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
/_build
Output
/chocolatey/tools/AU
/chocolatey/tools/install.ps1
/chocolatey/*.nupkg
Expand Down
323 changes: 323 additions & 0 deletions Chocolatey-AU.build.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,323 @@
param(
[string]
$OutputDirectory = "$PSScriptRoot/Output",


[string]
$TimeStampServer = $(
if ($env:CERT_TIMESTAMP_URL) {
$env:CERT_TIMESTAMP_URL
}
else {
'http://timestamp.digicert.com'
}
),

[string]
$CertificatePath = $env:CHOCOLATEY_OFFICIAL_CERT,

[string]
$CertificatePassword = $env:CHOCOLATEY_OFFICIAL_CERT_PASSWORD,


[string]
$CertificateAlgorithm = $(
if ($env:CERT_ALGORITHM) {
$env:CERT_ALGORITHM
}
else {
'Sha256'
}
),

[string]
$CertificateSubjectName = "Chocolatey Software, Inc.",


[string]
$NugetApiKey = $env:POWERSHELLPUSH_API_KEY,


[string]
$PublishUrl = $env:POWERSHELLPUSH_SOURCE,


[string]
$ModuleName = 'Chocolatey-AU',


[switch]
$ThrowOnPSSAViolation
)

$ErrorActionPreference = 'Stop'

$script:SourceFolder = "$PSScriptRoot/src"
$script:ReleaseBuild = -not [string]::IsNullOrEmpty((git tag --points-at HEAD 2> $null) -replace '^v')
$script:BuildVersion = $null
$script:IsPrerelease = $false


# Fix for Register-PSRepository not working with https from StackOverflow:
# https://stackoverflow.com/questions/35296482/invalid-web-uri-error-on-register-psrepository/35296483#35296483
function Register-PSRepositoryFix {
[CmdletBinding()]
param (
[Parameter(Mandatory = $true)]
[String]
$Name,

[Parameter(Mandatory = $true)]
[Uri]
$SourceLocation,

[ValidateSet('Trusted', 'Untrusted')]
$InstallationPolicy = 'Trusted'
)

$ErrorActionPreference = 'Stop'

try {
Write-Verbose 'Trying to register via Register-PSRepository'
Register-PSRepository -Name $Name -SourceLocation $SourceLocation -InstallationPolicy $InstallationPolicy -ErrorAction Stop
Write-Verbose 'Registered via Register-PSRepository'
}
catch {
Write-Verbose 'Register-PSRepository failed, registering via workaround'

# Adding PSRepository directly to file
Register-PSRepository -Name $Name -SourceLocation $env:TEMP -InstallationPolicy $InstallationPolicy -ErrorAction Stop
$PSRepositoriesXmlPath = "$env:LOCALAPPDATA\Microsoft\Windows\PowerShell\PowerShellGet\PSRepositories.xml"
$repos = Import-Clixml -Path $PSRepositoriesXmlPath
$repos[$Name].SourceLocation = $SourceLocation.AbsoluteUri
$repos[$Name].PublishLocation = [uri]::new($SourceLocation, 'package').AbsoluteUri
$repos[$Name].ScriptSourceLocation = ''
$repos[$Name].ScriptPublishLocation = ''
$repos | Export-Clixml -Path $PSRepositoriesXmlPath

# Reloading PSRepository list
Set-PSRepository -Name PSGallery -InstallationPolicy Trusted
Write-Verbose 'Registered via workaround'
}
}

# Synopsis: ensure GitVersion is installed
task InstallGitVersion {
if (-not (Get-Command gitversion -ErrorAction Ignore)) {
Write-Host "Gitversion not installed. Attempting to install"

if (-not ([Security.Principal.WindowsPrincipal]([Security.Principal.WindowsIdentity]::GetCurrent())).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)){
throw "You are not an administrator. We cannot use Chocolatey to install gitversion.portable."
}

choco install gitversion.portable -y --no-progress
}
}

# Synopsis: ensure PowerShellGet has the NuGet provider installed
task BootstrapPSGet {
if (-not (Get-PackageProvider NuGet -ErrorAction Ignore)) {
Write-Host "Installing NuGet package provider"
Install-PackageProvider NuGet -MinimumVersion 2.8.5.201 -ForceBootstrap -Force
}

Set-PSRepository -Name PSGallery -InstallationPolicy Trusted

if (-not (Get-InstalledModule PowerShellGet -MinimumVersion 2.0 -MaximumVersion 2.99 -ErrorAction Ignore)) {
Install-Module PowerShellGet -MaximumVersion 2.99 -Force -AllowClobber -Scope CurrentUser
Remove-Module PowerShellGet -Force
Import-Module PowerShellGet -MinimumVersion 2.0 -Force
}
}

# Synopsis: ensure Pester is installed
task InstallPester BootstrapPSGet, {
if (-not (Get-InstalledModule Pester -MaximumVersion 4.99 -ErrorAction SilentlyContinue)) {
Write-Host "Installing Pester"
Install-Module Pester -MaximumVersion 4.99 -SkipPublisherCheck -Force -Scope CurrentUser -ErrorAction Stop -Verbose:$false
}
}

# Synopsis: ensure PSScriptAnalyzer is installed
task InstallScriptAnalyzer BootstrapPSGet, {
if (-not (Get-InstalledModule PSScriptAnalyzer -MinimumVersion 1.20 -ErrorAction SilentlyContinue)) {
Write-Host "Installing PSSA"
Install-Module PSScriptAnalyzer -Scope CurrentUser -Force -MinimumVersion 1.20 -ErrorAction Stop -Verbose:$false
}
}

# Synopsis: cleanup build artifacts
task Clean {
Write-Host "Removing any prior existing files from $OutputDirectory"
remove $OutputDirectory
$null = New-Item -Path $OutputDirectory -ItemType Directory
}

# Synopsis: run PSScriptAnalyzer on project files
task ScriptAnalyzer InstallScriptAnalyzer, {
Write-Host "Checking project files with PSScriptAnalyzer"
$results = Invoke-ScriptAnalyzer -Path $script:SourceFolder -Recurse -Settings "$PSScriptRoot/PSScriptAnalyzerSettings.psd1"
if ($results) {
Write-Warning "$($results.Count) PSSA rule violations found."
$results | Format-Table -AutoSize | Out-String | Write-Host -ForegroundColor yellow
# Chocolatey-AU currently has lots of PSSA violations. None of them are errors in PSSA.
# For now, the build will not fail on PSSA unless asked.
if ($ThrowOnPSSAViolation) {
throw "PSSA rule violations detected, see above errors for more information"
}
}
}

# Synopsis: build the project
task Build Clean, InstallGitVersion, ScriptAnalyzer, {
$null = New-Item "$OutputDirectory/$ModuleName" -ItemType Directory

Copy-Item "$script:SourceFolder/*" -Destination "$OutputDirectory/$ModuleName" -Recurse
$manifest = Get-ChildItem "$OutputDirectory/$ModuleName/$ModuleName.psd1"

$gitversion = gitversion.exe
$gitversion | Out-String -Width 120 | Write-Host
$versionInfo = $gitversion | ConvertFrom-Json
$manifestUpdates = @{
Path = $manifest.FullName
ModuleVersion = $versionInfo.MajorMinorPatch
}

$prerelease = $versionInfo.NuGetPreReleaseTagV2 -replace '[^a-z0-9]'
if ($prerelease) {
if ($prerelease -notmatch '^(alpha|beta)') {
$prerelease = "alpha$prerelease"
}

$manifestUpdates.Prerelease = $prerelease
$script:IsPrerelease = $true
}

$script:BuildVersion = if ($prerelease) {
"$($versionInfo.MajorMinorPatch)-$prerelease"
}
else {
$versionInfo.MajorMinorPatch
}

Update-ModuleManifest @manifestUpdates
}

task ImportChecks -After Build {
$publicFunctions = Get-Item "$script:SourceFolder/Public/*.ps1"

Remove-Module $ModuleName -ErrorAction Ignore
Import-Module "$OutputDirectory/$ModuleName" -Force
$actualFunctions = (Get-Module $ModuleName).ExportedFunctions
if ($actualFunctions.Count -lt $publicFunctions.Count) {
$missingFunctions = $publicFunctions.BaseName | Where-Object { $_ -notin $actualFunctions.Keys }
$message = @(
"src/Public: $($publicFunctions.Count) files"
"${ModuleName}: $($actualFunctions.Count) exported functions"
"some functions in the Public folder may not be exported"
"missing functions may include: $($missingFunctions -join ', ')"
) -join "`n"
Write-Warning $message
}
elseif ($publicFunctions.Count -lt $actualFunctions.Count) {
$message = @(
"src/Public: $($publicFunctions.Count) files"
"${ModuleName}: $($actualFunctions.Count) exported functions"
"there seems to be fewer files in the Public folder than public functions exported"
) -join "`n"
Write-Warning $message
}
}

# Synopsis: CI-specific build operations to run after the normal build
task CIBuild Build, {
Write-Host $env:GitVersionTool

Write-Host "##teamcity[buildNumber '$script:BuildVersion']"
}

# Synopsis: run Pester tests
task Test InstallPester, Build, {
Import-Module Pester -MaximumVersion 4.99

Copy-Item -Path "$script:SourceFolder/../Tests" -Destination "$OutputDirectory/Tests" -Recurse
$results = Invoke-Pester (Resolve-Path "$OutputDirectory/Tests") -OutputFile "$OutputDirectory/test.results.xml" -OutputFormat NUnitXml -PassThru

assert ($results.FailedCount -eq 0) "Pester test failures found, see above or the '$OutputDirectory/test.results.xml' result file for details"
}

# Synopsis: generate documentation files
task GenerateDocs {
& "$PSScriptRoot/mkdocs.ps1"
}

# Synopsis: sign PowerShell scripts
task Sign Build, {
Write-Host "Signing PowerShell files"
$signParams = @{
CertificateAlgorithm = $CertificateAlgorithm
TimeStampServer = $TimeStampServer
ScriptsToSign = Get-ChildItem -Path "$OutputDirectory/$ModuleName" -Recurse -Include '*.ps1', '*.psm1'
}

if ($CertificatePath) {
$signParams.CertificatePath = $CertificatePath
$signParams.CertificatePassword = $CertificatePassword
}
else {
$signParams.CertificateSubjectName = $CertificateSubjectName
}

& "$PSScriptRoot/sign.ps1" @signParams
}

# Synopsis: publish $ModuleName either internally or to the PSGallery
task Publish -If ($script:ReleaseBuild -or $PublishUrl) Build, {
if (-not (Test-Path $OutputDirectory)) {
throw 'Build the module with `Invoke-Build` or `build.ps1` before attempting to publish the module'
}

if (-not $NugetApiKey) {
throw 'Please pass the API key for publishing to the `-NugetApiKey` parameter or set $env:NugetApiKey before publishing'
}

$psdFile = Resolve-Path "$OutputDirectory/$ModuleName"
$publishParams = @{
Path = $psdFile
NugetApiKey = $NugetApiKey
}

if ($PublishUrl) {
Write-Verbose "Publishing to '$PublishUrl'"
$repo = Get-PSRepository | Where-Object PublishLocation -EQ $PublishUrl
if ($repo) {
$publishParams.Repository = $repo.Name
}
else {
$testRepo = @{
Name = "$ModuleName"
SourceLocation = $PublishUrl
InstallationPolicy = 'Trusted'
}

Register-PSRepositoryFix @testRepo
$publishParams.Repository = "$ModuleName"
}

Publish-Module @publishParams
}

if ($script:ReleaseBuild) {
Write-Verbose "Publishing to PSGallery"
$publishParams.NugetApiKey = $env:POWERSHELLGALLERY_API_KEY
$publishParams.Repository = 'PSGallery'

Publish-Module @publishParams
}
}

# Synopsis: CI configuration; test, build, sign the module, and publish
task CI CIBuild, Sign, Test, Publish

# Synopsis: default task; build and test
task . Build, Test
21 changes: 21 additions & 0 deletions GitVersion.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
mode: Mainline
assembly-versioning-format: '{Major}.{Minor}.{Patch}.{env:BUILDCOUNT ?? 0}'
assembly-informational-format: '{NuGetVersionV2}+Build.{env:BUILDCOUNT ?? 0}.Date.{CommitDate}.Branch.{env:SAFEBRANCHNAME ?? unknown}.Sha.{Sha}'
major-version-bump-message: '\+?semver:\s?(breaking|major)'
minor-version-bump-message: '\+?semver:\s?(feature|minor)'
patch-version-bump-message: '\+?semver:\s?(fix|patch)'
no-bump-message: '\+?semver:\s?(none|skip)'
branches:
master:
increment: Patch
pull-request:
tag: rc
increment: Patch
feature:
increment: Patch
regex: .*?/
source-branches:
- master
- feature
ignore:
commits-before: 2022-10-31T12:08:00
Loading

0 comments on commit 27cb8d9

Please sign in to comment.