Testing/Unit/PowerShell/CyberConfig/CyberConfig.JsonDefaults.Tests.ps1

using module '..\..\..\..\Modules\CyberConfig\CyberConfigValidator.psm1'
using module '..\..\..\..\Modules\CyberConfig\CyberConfig.psm1'

InModuleScope CyberConfig {
Describe "JSON-based Configuration System" {
    BeforeAll {
        # Initialize the system
        [CyberConfig]::InitializeValidator()
    }

    Context "System Initialization" {
        It "Should initialize the validator successfully" {
            { [CyberConfig]::InitializeValidator() } | Should -Not -Throw
        }

        It "Should load configuration defaults from JSON" {
            $defaults = [CyberConfig]::GetConfigDefaults()
            $defaults | Should -Not -BeNullOrEmpty
        }

        It "Should load configuration schema from JSON" {
            $schema = [CyberConfig]::GetConfigSchema()
            $schema | Should -Not -BeNullOrEmpty
        }
    }

    Context "Default Values from JSON" {
        It "Should read DisconnectOnExit default as false from JSON" {
            $disconnectDefault = [CyberConfig]::CyberDefault('DefaultDisconnectOnExit')
            $disconnectDefault | Should -Be $false
        }

        It "Should read LogIn default as true from JSON" {
            $loginDefault = [CyberConfig]::CyberDefault('DefaultLogIn')
            $loginDefault | Should -Be $true
        }

        It "Should read OPAVersion default from JSON" {
            # Read the expected value directly from the JSON file
            $jsonDefaults = Get-Content "$PSScriptRoot\..\..\..\..\Modules\CyberConfig\CyberConfigDefaults.json" -Raw | ConvertFrom-Json
            $expectedVersion = $jsonDefaults.defaults.OPAVersion

            # Verify CyberConfig returns the same value
            $opaVersion = [CyberConfig]::CyberDefault('DefaultOPAVersion')
            $opaVersion | Should -Be $expectedVersion
        }

        It "Should read M365Environment default as commercial from JSON" {
            $environment = [CyberConfig]::CyberDefault('DefaultM365Environment')
            $environment | Should -Be "commercial"
        }

        It "Should read ProductNames default from JSON" {
            $productNames = [CyberConfig]::CyberDefault('DefaultProductNames')
            $productNames | Should -Contain "aad"
            $productNames | Should -Contain "defender"
            $productNames | Should -Contain "exo"
        }

        It "Should read OutFolderName default from JSON" {
            $folderName = [CyberConfig]::CyberDefault('DefaultOutFolderName')
            $folderName | Should -Be "M365BaselineConformance"
        }
    }

    Context "JSON Structure Validation" {
        It "Should have AllProductNames defined in defaults" {
            $defaults = [CyberConfig]::GetConfigDefaults()
            $defaults.defaults.AllProductNames | Should -Not -Be NullOrEmpty
            $defaults.defaults.AllProductNames.Count | Should -BeGreaterThan 0
        }

        It "Should have M365Environment default defined" {
            $defaults = [CyberConfig]::GetConfigDefaults()
            $defaults.defaults.M365Environment | Should -Not -BeNullOrEmpty
            $defaults.defaults.M365Environment | Should -Be "commercial"
        }

        It "Should have validation settings defined" {
            $defaults = [CyberConfig]::GetConfigDefaults()
            $defaults.validation | Should -Not -BeNullOrEmpty
            $defaults.validation.policyIdPattern | Should -Not -BeNullOrEmpty
        }

        It "Should have privileged roles defined" {
            $defaults = [CyberConfig]::GetConfigDefaults()
            $defaults.privilegedRoles | Should -Not -BeNullOrEmpty
            $defaults.privilegedRoles.Count | Should -BeGreaterThan 0
        }
    }

    Context "Product Information" {
        It "Should provide product information for supported products" {
            $aadInfo = [CyberConfig]::GetProductInfo('aad')
            $aadInfo | Should -Not -BeNullOrEmpty
            $aadInfo.name | Should -Be "aad"
        }

        It "Should return supported products list" {
            $supportedProducts = [CyberConfig]::GetSupportedProducts()
            $supportedProducts | Should -Contain "aad"
            $supportedProducts | Should -Contain "defender"
        }

        It "Should return supported environments list" {
            $supportedEnvironments = [CyberConfig]::GetSupportedEnvironments()
            $supportedEnvironments | Should -Contain "commercial"
            $supportedEnvironments | Should -Contain "gcc"
        }
    }

    Context "No Hardcoded Values" {
        It "Should not use hardcoded DisconnectOnExit value" {
            # This test ensures the value comes from JSON, not hardcoded
            $jsonDefaults = Get-Content "$PSScriptRoot\..\..\..\..\Modules\CyberConfig\CyberConfigDefaults.json" | ConvertFrom-Json
            $jsonValue = $jsonDefaults.defaults.DisconnectOnExit
            $configValue = [CyberConfig]::CyberDefault('DefaultDisconnectOnExit')
            $configValue | Should -Be $jsonValue
        }

        It "Should read all default values from JSON file" {
            $jsonDefaults = Get-Content "$PSScriptRoot\..\..\..\..\Modules\CyberConfig\CyberConfigDefaults.json" | ConvertFrom-Json

            # Test key values match between JSON and CyberConfig
            [CyberConfig]::CyberDefault('DefaultLogIn') | Should -Be $jsonDefaults.defaults.LogIn
            [CyberConfig]::CyberDefault('DefaultM365Environment') | Should -Be $jsonDefaults.defaults.M365Environment
            [CyberConfig]::CyberDefault('DefaultOPAVersion') | Should -Be $jsonDefaults.defaults.OPAVersion
        }
    }

    AfterAll {
        [CyberConfig]::ResetInstance()
    }
}
}