Skip to content
This repository has been archived by the owner on Jul 18, 2024. It is now read-only.

Commit

Permalink
Archive module preview 1 PR (#131)
Browse files Browse the repository at this point in the history
* Add .gitattributes, .gitignore, and README.md.

* Add project files.

* added path helper, archive entry

* updated path helper

* resolved bug where GetEntryName was throwing an ArgumentException

* fixed a bug, started work on zip support

* worked on zip archive support

* added ArchiveFactory class

* imporved zip support

* fixed a bug in tests, added error handling for DestinationPath

* fixed bug in tests where Test-ZipArchive was not working correctly

* added tests for DestinationPath

* added additional tests, added TODOs

* updated tests

* added resx files for messages, refactored code, updated structure, etc.

* refactored PathHelper class

* worked on automatically determining archive format based on DestinationPath's extension

* added support for determining archive format automatically based on DestinationPath's extension

* fixed a bug with archive format warning, added TarArchive file

* renamed Action to WriteMode, fixed bug with compressing directories, added support for tar, added support for overwrite

* fixed bug where the directory structure of directories was not being preserved, fixed bug where error and warning messages were not being shown

* addded exception handling to PathHelper class

* removed files from git, removed tar support for preview release, added psd1 file

* updated build script, updated exception handling in PathHelper

* used FileSystemInfo instead of String to store full path information

* updated checking for the same source path and destination path

* updated build configuration

* updated project version with prelease info, removed tar support after merging branches

* updated CI config, fixed bug with missing error message, fixed tests

* updated CI to build module and run tests across all platforms

* updated CI to run tests, added and reorganized tests, solved a bug where overwriting the working directory could succeed

* used pascal case for ArchiveFormat enum members, refactored some code based on feedback

* fixed formatting for multiple files, updated csproj to generate Messages.Designer.cs and to remove debug symbols in Release config

* fixed missing quotation mark in CI config, updated switch code in ArchiveFactory.TryGetArchiveFormatFromExtension, added another list to keep track of paths from -LiteralPath and -Path seperately

* added assertions to prevent possible null error, added RequiredVersion when installing Pester in tests script, removed default valuesm in parameter attributes, and other minor changes

* added localized messages for Add, Create, and progress bar text, minor formatting changes

* added copyright header, removed usage of DS in tests, minor formatting changes

* updated .gitignore, added explanation for why ArchiveAddition.EntryName is not necessarily equal to FileSystemInfo.Name

* updated Compress-Archive cmdlet to resolve a path one at a time rather than collecting all paths first

* fixed a bug where PathNotFound error was not thrown, fixed a bug when testing invalid paths

* added custom assertions for testing zip archives

* updated CI to run tests using new assertion, updated README with Azure CI status, fixed a bug where a path is determined to be relative to the working directory if the working directory is on a different drive than the path

Co-authored-by: t-ayousuf <t-ayousuf@DESKTOP-SU5OBBS>
Co-authored-by: Abdullah Yousuf <[email protected]>
  • Loading branch information
3 people authored Aug 11, 2022
1 parent 0d4537d commit b783599
Show file tree
Hide file tree
Showing 38 changed files with 4,910 additions and 2,829 deletions.
79 changes: 37 additions & 42 deletions .azdevops/CI.yml
Original file line number Diff line number Diff line change
Expand Up @@ -27,51 +27,46 @@ stages:
displayName: Build module
steps:

- pwsh: |
& $(Build.SourcesDirectory)\SimpleBuild.ps1
displayName: Build Microsoft.PowerShell.Archive module
condition: succeededOrFailed()
- task: UseDotNet@2
displayName: 'Get .NET 7.0 SDK'
inputs:
packageType: sdk
version: 7.x
includePreviewVersions: true

- pwsh: |
dir "$(BuildOutDir)\*" -Recurse
displayName: Show BuildOutDirectory
- template: Sbom.yml@ComplianceRepo
parameters:
BuildDropPath: "$(BuildOutDir)"
Build_Repository_Uri: 'https://github.com/PowerShell/Microsoft.PowerShell.Archive'
PackageName: $(PackageName)
PackageVersion: $(PackageVersion)

- pwsh: |
dir "$(BuildOutDir)\*" -Recurse
displayName: Show BuildOutDirectory
& "$(Build.SourcesDirectory)\Build.ps1"
displayName: Build Microsoft.PowerShell.Archive module
- pwsh: |
$signSrcPath = "$(BuildOutDir)"
# Set signing src path variable
$vstsCommandString = "vso[task.setvariable variable=signSrcPath]${signSrcPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
$signOutPath = "$(Build.SourcesDirectory)\signed\Microsoft.PowerShell.Archive"
$null = New-Item -ItemType Directory -Path $signOutPath
# Set signing out path variable
$vstsCommandString = "vso[task.setvariable variable=signOutPath]${signOutPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
# Set path variable for guardian codesign validation
$vstsCommandString = "vso[task.setvariable variable=GDN_CODESIGN_TARGETDIRECTORY]${signOutPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
displayName: Setup variables for signing
- task: CopyFiles@2
displayName: 'Copy build'
inputs:
sourceFolder: '$(BuildOutDir)'
contents: '**'
targetFolder: '$(Build.ArtifactStagingDirectory)/Microsoft.PowerShell.Archive'

- pwsh: |
Copy-Item -Path "$(signSrcPath)\*" -Destination "$(signOutPath)"
displayName: Fake Signing
- publish: '$(Build.ArtifactStagingDirectory)/Microsoft.PowerShell.Archive'
displayName: 'Publish module build'
artifact: ModuleBuild

- pwsh: |
Compress-Archive -Path "$(signOutPath)\*" -DestinationPath "$(System.ArtifactsDirectory)\Microsoft.PowerShell.Archive.zip"
displayName: Create Microsoft.PowerShell.Archive.zip
- stage: Test
dependsOn: Build
displayName: Run tests
jobs:
- template: TestsTemplate.yml
parameters:
vmImageName: windows-2019
jobName: run_test_windows
jobDisplayName: Run Windows tests

- publish: $(System.ArtifactsDirectory)\Microsoft.PowerShell.Archive.zip
artifact: SignedModule
- template: TestsTemplate.yml
parameters:
vmImageName: ubuntu-latest
jobName: run_test_linux
jobDisplayName: Run Linux tests

- template: TestsTemplate.yml
parameters:
vmImageName: macos-latest
jobName: run_test_macos
jobDisplayName: Run macOS tests
138 changes: 138 additions & 0 deletions .azdevops/ReleaseBuildPipeline.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
name: Microsoft.PowerShell.Archive-$(Build.BuildId)
trigger: none

pr: none

variables:
DOTNET_CLI_TELEMETRY_OPTOUT: 1
POWERSHELL_TELEMETRY_OPTOUT: 1

resources:
repositories:
- repository: ComplianceRepo
type: github
endpoint: ComplianceGHRepo
name: PowerShell/compliance
ref: master

stages:
- stage: Build
displayName: Build
pool:
name: 1ES
demands:
- ImageOverride -equals PSMMS2019-Secure
jobs:
- job: Build_Job
displayName: Build Microsoft.PowerShell.Archive
variables:
- group: ESRP
steps:
- checkout: self

- task: UseDotNet@2
displayName: 'Get .NET 7.0 SDK'
inputs:
packageType: sdk
version: 7.x
includePreviewVersions: true

- pwsh: |
& $(Build.SourcesDirectory)/Microsoft.PowerShell.Archive/SimpleBuild.ps1
displayName: Build Microsoft.PowerShell.Archive module
- pwsh: |
Get-ChildItem "$(BuildOutDir)\*" -Recurse | Write-Verbose -Verbose
displayName: Show BuildOutDirectory
- pwsh: |
$signSrcPath = "$(BuildOutDir)"
# Set signing src path variable
$vstsCommandString = "vso[task.setvariable variable=signSrcPath]${signSrcPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
# Get the module version
$ManifestPath = Join-Path $(BuildOutDir) "Microsoft.PowerShell.Archive.psd1"
$ManifestData = Import-PowerShellDataFile -Path $ManifestPath
$Version = $ManifestData.ModuleVersion
$signOutPath = "$(Build.SourcesDirectory)\signed\Microsoft.PowerShell.Archive\${Version}"
$null = New-Item -ItemType Directory -Path $signOutPath
# Set signing out path variable
$vstsCommandString = "vso[task.setvariable variable=signOutPath]${signOutPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
# Set path variable for guardian codesign validation
$vstsCommandString = "vso[task.setvariable variable=GDN_CODESIGN_TARGETDIRECTORY]${signOutPath}"
Write-Host "sending " + $vstsCommandString
Write-Host "##$vstsCommandString"
displayName: Setup variables for signing
- checkout: ComplianceRepo

- task: UseDotNet@2
displayName: 'Get .NET 2.1 SDK'
inputs:
packageType: sdk
version: 2.x
includePreviewVersions: true

- template: EsrpSign.yml@ComplianceRepo
parameters:
# the folder which contains the binaries to sign
buildOutputPath: $(signSrcPath)
# the location to put the signed output
signOutputPath: $(signOutPath)
# the certificate ID to use
certificateId: "CP-230012"
# the file pattern to use, comma separated
pattern: '*.psd1,*.dll'

- template: Sbom.yml@ComplianceRepo
parameters:
BuildDropPath: $(signOutPath)
Build_Repository_Uri: 'https://github.com/PowerShell/Microsoft.PowerShell.Archive'

- pwsh: |
Get-ChildItem $(signOutPath) -Recurse | Write-Output
- pwsh: |
Set-Location "$(Build.SourcesDirectory)"
# signOutPath points to directory with version number -- we want to point to the parent of that directory
$ModulePath = Split-Path $(signOutPath) -Parent
$(Build.SourcesDirectory)/Microsoft.PowerShell.Archive/.azdevops/SignAndPackageModule.ps1 -SignedPath $ModulePath
Get-ChildItem -recurse -file -name | Write-Verbose -Verbose
displayName: package build
- publish: "$(signSrcPath)"
artifact: build
displayName: Publish build

- stage: compliance
displayName: Compliance
dependsOn: Build
jobs:
- job: Compliance_Job
pool:
name: 1ES # Package ES CodeHub Lab E
steps:
- checkout: self
- checkout: ComplianceRepo
- download: current
artifact: build

- pwsh: |
Get-ChildItem -Path "$(Pipeline.Workspace)\build" -Recurse
displayName: Capture downloaded artifacts
- template: script-module-compliance.yml@ComplianceRepo
parameters:
# component-governance
sourceScanPath: '$(Build.SourcesDirectory)\Microsoft.PowerShell.Archive\src'
# credscan
suppressionsFile: ''
# TermCheck
optionsRulesDBPath: ''
optionsFTPath: ''
# tsa-upload
codeBaseName: 'PSNativeCommandProxy_2020'
# selections
APIScan: false # set to false when not using Windows APIs.
29 changes: 29 additions & 0 deletions .azdevops/RunTests.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# Copyright (c) Microsoft Corporation.
# Licensed under the MIT License.

# Import the built module
Import-Module "$env:PIPELINE_WORKSPACE/ModuleBuild/Microsoft.PowerShell.Archive.psd1"

Get-ChildItem "$env:PIPELINE_WORKSPACE/ModuleBuild" | Write-Verbose -Verbose

$pesterMinVersion = "5.3.0"
$pesterMaxVersion = "5.3.9"

# If Pester 5.3.x is not installed, install it
$pesterModule = Get-InstalledModule -Name "Pester" -MinimumVersion $pesterMinVersion -MaximumVersion $pesterMaxVersion
if ($null -eq $pesterModule) {
Install-Module -Name "Pester" -MinimumVersion $pesterMinVersion -MaximumVersion $pesterMaxVersion -Force
}

# Load Pester
Import-Module -Name "Pester" -MinimumVersion $pesterMinVersion -MaximumVersion $pesterMaxVersion

# Run tests
$OutputFile = "$PWD/build-unit-tests.xml"
$results = $null
$results = Invoke-Pester -Script ./Tests/Compress-Archive.Tests.ps1 -OutputFile $OutputFile -PassThru -OutputFormat NUnitXml -Show Failed, Context, Describe, Fails
Write-Host "##vso[artifact.upload containerfolder=testResults;artifactname=testResults]$OutputFile"
if(!$results -or $results.FailedCount -gt 0 -or !$results.TotalCount)
{
throw "Build or tests failed. Passed: $($results.PassedCount) Failed: $($results.FailedCount) Total: $($results.TotalCount)"
}
44 changes: 44 additions & 0 deletions .azdevops/SignAndPackageModule.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
# Copyright (c) Microsoft Corporation.
# Licensed under the MIT License.
[CmdletBinding(SupportsShouldProcess=$true)]
param (
[string]$SignedPath
)


$root = (Resolve-Path -Path "${PSScriptRoot}/../")[0]
$Name = "Microsoft.PowerShell.Archive"
$BuildOutputDir = Join-Path $root "\src\bin\Release"
$ManifestPath = "${BuildOutputDir}\${Name}.psd1"
$ManifestData = Import-PowerShellDataFile -Path $ManifestPath
$Version = $ManifestData.ModuleVersion

# this takes the files for the module and publishes them to a created, local repository
# so the nupkg can be used to publish to the PSGallery
function Export-Module
{
[System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("PSAvoidUsingWriteHost", "")]
param()
$packageRoot = $SignedPath

if ( -not (Test-Path $packageRoot)) {
throw "'$PubDir' does not exist"
}

# now constuct a nupkg by registering a local repository and calling publish module
$repoName = [guid]::newGuid().ToString("N")
Register-PSRepository -Name $repoName -SourceLocation $packageRoot -InstallationPolicy Trusted
Publish-Module -Path $packageRoot -Repository $repoName
Unregister-PSRepository -Name $repoName
Get-ChildItem -Recurse -Name $packageRoot | Write-Verbose
$nupkgName = "{0}.{1}-preview1.nupkg" -f ${Name},${Version}
$nupkgPath = Join-Path $packageRoot $nupkgName
if ($env:TF_BUILD) {
# In Azure DevOps
Write-Host "##vso[artifact.upload containerfolder=$nupkgName;artifactname=$nupkgName;]$nupkgPath"
}
}

# The SBOM should already be in -SignedPath, so there is no need to copy it

Export-Module
94 changes: 94 additions & 0 deletions .azdevops/TestsTemplate.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
parameters:
- name: vmImageName
type: string
default: 'windows-2019'

- name: jobName
type: string
default: 'run_test_windows'

- name: jobDisplayName
type: string
default: 'Run test'

jobs:
- job: '${{ parameters.jobName }}'
pool:
vmImage: ${{ parameters.vmImageName }}
displayName: ${{ parameters.jobDisplayName }}
steps:
- download: current
artifact: ModuleBuild

- pwsh: |
Write-Output ${{ parameters.vmImageName }}
if ("${{ parameters.vmImageName }}" -like 'windows-*')
{
$url = "https://github.com/PowerShell/PowerShell/releases/download/v7.3.0-preview.6/PowerShell-7.3.0-preview.6-win-x64.zip"
$downloadFilename = "pwsh_download.msi"
}
if ("${{ parameters.vmImageName }}" -like 'macos-*')
{
$url = "https://github.com/PowerShell/PowerShell/releases/download/v7.3.0-preview.6/powershell-7.3.0-preview.6-osx-x64.pkg"
$downloadFilename = "pwsh_download.pkg"
}
if ("${{ parameters.vmImageName }}" -like 'ubuntu-*')
{
$url = "https://github.com/PowerShell/PowerShell/releases/download/v7.3.0-preview.6/powershell-7.3.0-preview.6-linux-x64.tar.gz"
$downloadFilename = "pwsh_download.tar.gz"
}
$downloadDestination = Join-Path $pwd $downloadFilename
Invoke-WebRequest -Uri $url -OutFile $downloadDestination
# Installation steps for windows
if ("${{ parameters.vmImageName }}" -like 'windows-*') {
Expand-Archive -Path $downloadDestination -DestinationPath "pwsh-preview"
$powerShellPreview = Join-Path $pwd "pwsh-preview" "pwsh.exe"
}
if ("${{ parameters.vmImageName }}" -like 'ubuntu-*')
{
gunzip -d $downloadDestination
$downloadDestination = $downloadDestination.Replace(".gz", "")
mkdir "pwsh-preview"
tar -x -f $downloadDestination -C "pwsh-preview"
$powerShellPreview = Join-Path $pwd "pwsh-preview" "pwsh"
}
if ("${{ parameters.vmImageName }}" -like 'macos-*')
{
sudo xattr -rd com.apple.quarantine "${downloadDestination}"
sudo installer -pkg "${downloadDestination}" -target /
$powerShellPreview = "pwsh-preview"
}
# Write the location of PowerShell Preview
Write-Host "##vso[task.setvariable variable=PowerShellPreviewExecutablePath;]$powershellPreview"
displayName: Download and Install PowerShell Preview
- pwsh: |
$destination = Join-Path $pwd "7z.exe"
$installUrl = "https://www.7-zip.org/a/7z2201-x64.exe"
Invoke-WebRequest -Uri $installUrl -OutFile $destination
# Run the installer in silent mode
.$destination /S /D="C:\Program Files\7-Zip"
displayName: Install 7-zip
condition: and(succeeded(), startswith('${{ parameters.vmImageName }}', 'windows'))
- pwsh: |
if ("${{ parameters.vmImageName }}" -like 'windows-*')
{
# Add 7-zip to PATH on Windows
[System.Environment]::SetEnvironmentVariable('PATH',$Env:PATH+';C:\Program Files\7-zip')
}
"$(PowerShellPreviewExecutablePath) .azdevops/RunTests.ps1" | Invoke-Expression
displayName: Run Tests
- task: PublishTestResults@2
displayName: 'Publish Test Results **/*tests.xml'
inputs:
testResultsFormat: NUnit
testResultsFiles: '**/*tests.xml'
testRunTitle: 'Build Unit Tests'
continueOnError: true
condition: succeededOrFailed()
Loading

0 comments on commit b783599

Please sign in to comment.