Testing/Unit/PowerShell/Support/Update-CyberAssessment.tests.ps1

Import-Module (Join-Path -Path $PSScriptRoot -ChildPath '../../../../Modules/Support')

InModuleScope 'Support' {
    Describe "Update-CyberAssessment" {
        BeforeAll {
            # Load the actual CyberAssessment version from the manifest
            $ManifestPath = Join-Path -Path $PSScriptRoot -ChildPath "..\..\..\..\CyberAssessment.psd1"
            if (Test-Path -Path $ManifestPath) {
                $manifestData = Import-PowerShellDataFile -Path $ManifestPath
                $script:CurrentCyberAssessmentVersion = [version]$manifestData.ModuleVersion
            } else {
                throw "Could not find CyberAssessment.psd1 at expected path: $ManifestPath"
            }

            # Create test versions based on actual version
            $script:MockNewerVersion = [version]"$($script:CurrentCyberAssessmentVersion.Major).$($script:CurrentCyberAssessmentVersion.Minor + 1).0"
            $script:MockOlderVersion = [version]"$($script:CurrentCyberAssessmentVersion.Major).$($script:CurrentCyberAssessmentVersion.Minor - 1).0"

            # For GitHub container
            if (-not (Get-Command -Name 'Update-CyberAssessmentFromPSGallery' -ErrorAction SilentlyContinue)) {
                function script:Update-CyberAssessmentFromPSGallery { }
            }
            if (-not (Get-Command -Name 'Update-CyberAssessmentFromGitHub' -ErrorAction SilentlyContinue)) {
                function script:Update-CyberAssessmentFromGitHub { }
            }

            # Set up default mocks at BeforeAll level to ensure they're available
            Mock Write-Output { }
            Mock Write-Information { }
            Mock Write-Error { }
            Mock Write-Warning { }
            Mock Update-CyberAssessmentFromPSGallery { }
            Mock Update-CyberAssessmentFromGitHub { }
        }

        BeforeEach {
            Mock Write-Output { }
            Mock Write-Information { }
            Mock Write-Error { }
            Mock Write-Warning { }
            Mock Update-CyberAssessmentFromPSGallery { }
            Mock Update-CyberAssessmentFromGitHub { }
        }

        Context "PSGallery update scenarios" {
            It "Should call PSGallery update function with CurrentUser scope" {
                Update-CyberAssessment -Source PSGallery -Scope CurrentUser

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
                Assert-MockCalled Update-CyberAssessmentFromGitHub -Times 0
            }

            It "Should call PSGallery update function with AllUsers scope" {
                Update-CyberAssessment -Source PSGallery -Scope AllUsers

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
            }

            It "Should default to PSGallery source when not specified" {
                Update-CyberAssessment -Scope CurrentUser

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
                Assert-MockCalled Update-CyberAssessmentFromGitHub -Times 0
            }

            It "Should default to CurrentUser scope when not specified" {
                Update-CyberAssessment -Source PSGallery

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
            }
        }

        Context "GitHub update scenarios" {
            It "Should call GitHub update function" {
                Update-CyberAssessment -Source GitHub

                Assert-MockCalled Update-CyberAssessmentFromGitHub -Times 1
                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 0
            }
        }

        Context "Error handling scenarios" {
            It "Should handle invalid source parameter" {
                { Update-CyberAssessment -Source "InvalidSource" } | Should -Throw
            }

            It "Should handle invalid scope parameter" {
                { Update-CyberAssessment -Scope "InvalidScope" } | Should -Throw
            }
        }

        Context "Parameter validation" {
            It "Should accept valid Source parameter values" {
                { Update-CyberAssessment -Source PSGallery } | Should -Not -Throw
                { Update-CyberAssessment -Source GitHub } | Should -Not -Throw
            }

            It "Should accept valid Scope parameter values" {
                { Update-CyberAssessment -Scope CurrentUser } | Should -Not -Throw
                { Update-CyberAssessment -Scope AllUsers } | Should -Not -Throw
            }

            It "Should work with no parameters (defaults)" {
                { Update-CyberAssessment } | Should -Not -Throw

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
            }
        }

        Context "Integration with helper functions" {
            It "Should call appropriate helper function based on source" {
                Update-CyberAssessment -Source PSGallery -Scope AllUsers
                Update-CyberAssessment -Source GitHub

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
                Assert-MockCalled Update-CyberAssessmentFromGitHub -Times 1
            }

            It "Should pass through parameters correctly to PSGallery function" {
                Update-CyberAssessment -Source PSGallery -Scope AllUsers

                Assert-MockCalled Update-CyberAssessmentFromPSGallery -Times 1
            }
        }
    }
}