From fc9cfd5fb08f6efbad55ba8f3a5d2a989cbb2757 Mon Sep 17 00:00:00 2001 From: Matt Richardson Date: Wed, 3 Nov 2021 11:33:03 +1100 Subject: [PATCH] Convert tests from rspec to pester (#290) We've had a lot of trouble fighting with ruby - mainly around rubygems. It's just not fun. Combine that with unfamiliarity and a "why are we using ruby for tests when the rest of the code is in powershell" disconnect, it makes a lot of sense to use Pester as our test framework instead. --- .ruby-version | 1 - E2ETests/.rspec | 1 - E2ETests/Gemfile | 7 - E2ETests/Gemfile.lock | 64 -- E2ETests/Rakefile | 6 - .../Scenarios/Server_Scenario_01_Install.ps1 | 11 +- .../Server_Scenario_07_Reinstall.ps1 | 11 +- .../TestHelpers/Get-EnvironmentDetails.ps1 | 29 + .../Spec/TestHelpers/Get-SpaceDetails.ps1 | 26 + .../Spec/TestHelpers/Get-TentacleDetails.ps1 | 56 ++ .../Spec/TestHelpers/Get-WorkerDetails.ps1 | 43 ++ .../TestHelpers/Get-WorkerPoolDetails.ps1 | 29 + .../Private/Get-EnvironmentViaApi.ps1 | 25 + .../TestHelpers/Private/Get-Environments.ps1 | 19 + .../Private/Get-MachinePolicies.ps1 | 19 + .../TestHelpers/Private/Get-MachineViaApi.ps1 | 25 + .../TestHelpers/Private/Get-SpaceViaApi.ps1 | 21 + .../Spec/TestHelpers/Private/Get-Tenants.ps1 | 19 + .../TestHelpers/Private/Get-Thumbprint.ps1 | 16 + .../Private/Get-WorkerPoolViaApi.ps1 | 25 + .../TestHelpers/Private/Get-WorkerViaApi.ps1 | 25 + ...ollUntilMachineHasCompletedHealthCheck.ps1 | 35 ++ ...ntilWorkerHasCompletedHealthCheck copy.ps1 | 35 ++ .../Private/Test-IsTentacleOnline.ps1 | 28 + .../Private/Test-IsWorkerOnline.ps1 | 28 + .../Private/Test-ServerSupportsSpaces.ps1 | 13 + .../Spec/server_scenario_01_install.Tests.ps1 | 168 ++++++ .../Spec/server_scenario_01_install_spec.rb | 79 --- ..._scenario_02_install_second_node.Tests.ps1 | 143 +++++ ...er_scenario_02_install_second_node_spec.rb | 82 --- .../Spec/server_scenario_03_remove.Tests.ps1 | 71 +++ .../Spec/server_scenario_03_remove_spec.rb | 41 -- ...r_scenario_04_remove_second_node.Tests.ps1 | 68 +++ ...ver_scenario_04_remove_second_node_spec.rb | 37 -- ...nario_05_install_custom_instance.Tests.ps1 | 100 ++++ ...cenario_05_install_custom_instance_spec.rb | 42 -- ...enario_06_remove_custom_instance.Tests.ps1 | 68 +++ ...scenario_06_remove_custom_instance_spec.rb | 37 -- .../server_scenario_07_reinstall.Tests.ps1 | 114 ++++ .../Spec/server_scenario_07_reinstall_spec.rb | 47 -- .../Spec/server_scenario_08_upgrade.Tests.ps1 | 121 ++++ .../Spec/server_scenario_08_upgrade_spec.rb | 50 -- ...rver_scenario_09_watchdog_create.Tests.ps1 | 55 ++ ...server_scenario_09_watchdog_create_spec.rb | 12 - ...rver_scenario_10_watchdog_delete.Tests.ps1 | 53 ++ ...server_scenario_10_watchdog_delete_spec.rb | 12 - .../Spec/server_scenario_11_remove.Tests.ps1 | 68 +++ .../Spec/server_scenario_11_remove_spec.rb | 37 -- ...rver_scenario_12_built_in_worker.Tests.ps1 | 135 +++++ ...server_scenario_12_built_in_worker_spec.rb | 69 --- .../Spec/server_scenario_13_remove.Tests.ps1 | 68 +++ .../Spec/server_scenario_13_remove_spec.rb | 37 -- ...rio_14_install_without_configure.Tests.ps1 | 71 +++ ...nario_14_install_without_configure_spec.rb | 33 -- ..._configure_preinstalled_instance.Tests.ps1 | 112 ++++ ...15_configure_preinstalled_instance_spec.rb | 54 -- E2ETests/Spec/spec_helper.rb | 12 - .../tentacle_scenario_01_install.Tests.ps1 | 549 ++++++++++++++++++ .../Spec/tentacle_scenario_01_install_spec.rb | 246 -------- .../tentacle_scenario_02_remove.Tests.ps1 | 196 +++++++ .../Spec/tentacle_scenario_02_remove_spec.rb | 93 --- .../tentacle_scenario_03_reinstall.Tests.ps1 | 147 +++++ .../tentacle_scenario_03_reinstall_spec.rb | 54 -- .../tentacle_scenario_04_upgrade.Tests.ps1 | 157 +++++ .../Spec/tentacle_scenario_04_upgrade_spec.rb | 66 --- ...acle_scenario_05_watchdog_create.Tests.ps1 | 54 ++ ...ntacle_scenario_05_watchdog_create_spec.rb | 12 - ...acle_scenario_06_watchdog_delete.Tests.ps1 | 52 ++ ...ntacle_scenario_06_watchdog_delete_spec.rb | 12 - .../tentacle_scenario_07_remove.Tests.ps1 | 67 +++ .../Spec/tentacle_scenario_07_remove_spec.rb | 26 - ..._scenario_08_tentacle_comms_port.Tests.ps1 | 156 +++++ ...le_scenario_08_tentacle_comms_port_spec.rb | 65 --- Tests/OctopusDSC.Tests.ps1 | 2 +- .../configure-octopus-for-tentacle-tests.ps1 | 139 +++-- Tests/install-test-dependencies.ps1 | 51 -- Tests/surface-logs.ps1 | 40 -- vagrantfile | 84 +-- 78 files changed, 3432 insertions(+), 1549 deletions(-) delete mode 100644 .ruby-version delete mode 100644 E2ETests/.rspec delete mode 100644 E2ETests/Gemfile delete mode 100644 E2ETests/Gemfile.lock delete mode 100644 E2ETests/Rakefile create mode 100644 E2ETests/Spec/TestHelpers/Get-EnvironmentDetails.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Get-SpaceDetails.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Get-TentacleDetails.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Get-WorkerDetails.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Get-WorkerPoolDetails.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-EnvironmentViaApi.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-Environments.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-MachinePolicies.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-MachineViaApi.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-SpaceViaApi.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-Tenants.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-Thumbprint.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-WorkerPoolViaApi.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Get-WorkerViaApi.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilMachineHasCompletedHealthCheck.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilWorkerHasCompletedHealthCheck copy.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Test-IsTentacleOnline.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Test-IsWorkerOnline.ps1 create mode 100644 E2ETests/Spec/TestHelpers/Private/Test-ServerSupportsSpaces.ps1 create mode 100644 E2ETests/Spec/server_scenario_01_install.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_01_install_spec.rb create mode 100644 E2ETests/Spec/server_scenario_02_install_second_node.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_02_install_second_node_spec.rb create mode 100644 E2ETests/Spec/server_scenario_03_remove.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_03_remove_spec.rb create mode 100644 E2ETests/Spec/server_scenario_04_remove_second_node.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_04_remove_second_node_spec.rb create mode 100644 E2ETests/Spec/server_scenario_05_install_custom_instance.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_05_install_custom_instance_spec.rb create mode 100644 E2ETests/Spec/server_scenario_06_remove_custom_instance.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_06_remove_custom_instance_spec.rb create mode 100644 E2ETests/Spec/server_scenario_07_reinstall.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_07_reinstall_spec.rb create mode 100644 E2ETests/Spec/server_scenario_08_upgrade.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_08_upgrade_spec.rb create mode 100644 E2ETests/Spec/server_scenario_09_watchdog_create.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_09_watchdog_create_spec.rb create mode 100644 E2ETests/Spec/server_scenario_10_watchdog_delete.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_10_watchdog_delete_spec.rb create mode 100644 E2ETests/Spec/server_scenario_11_remove.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_11_remove_spec.rb create mode 100644 E2ETests/Spec/server_scenario_12_built_in_worker.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_12_built_in_worker_spec.rb create mode 100644 E2ETests/Spec/server_scenario_13_remove.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_13_remove_spec.rb create mode 100644 E2ETests/Spec/server_scenario_14_install_without_configure.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_14_install_without_configure_spec.rb create mode 100644 E2ETests/Spec/server_scenario_15_configure_preinstalled_instance.Tests.ps1 delete mode 100644 E2ETests/Spec/server_scenario_15_configure_preinstalled_instance_spec.rb delete mode 100644 E2ETests/Spec/spec_helper.rb create mode 100644 E2ETests/Spec/tentacle_scenario_01_install.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_01_install_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_02_remove.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_02_remove_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_03_reinstall.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_03_reinstall_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_04_upgrade.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_04_upgrade_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_05_watchdog_create.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_05_watchdog_create_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_06_watchdog_delete.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_06_watchdog_delete_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_07_remove.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_07_remove_spec.rb create mode 100644 E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port.Tests.ps1 delete mode 100644 E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port_spec.rb diff --git a/.ruby-version b/.ruby-version deleted file mode 100644 index 437459cd9..000000000 --- a/.ruby-version +++ /dev/null @@ -1 +0,0 @@ -2.5.0 diff --git a/E2ETests/.rspec b/E2ETests/.rspec deleted file mode 100644 index 49d5710b3..000000000 --- a/E2ETests/.rspec +++ /dev/null @@ -1 +0,0 @@ ---format documentation diff --git a/E2ETests/Gemfile b/E2ETests/Gemfile deleted file mode 100644 index 7186d0fb4..000000000 --- a/E2ETests/Gemfile +++ /dev/null @@ -1,7 +0,0 @@ -source "https://rubygems.org" - -gem "rake" -gem "serverspec" -gem "rspec-teamcity", "~> 0.0.1" -gem "nokogiri" -gem "octopus-serverspec-extensions", "~> 0.18.1" diff --git a/E2ETests/Gemfile.lock b/E2ETests/Gemfile.lock deleted file mode 100644 index d5f4978df..000000000 --- a/E2ETests/Gemfile.lock +++ /dev/null @@ -1,64 +0,0 @@ -GEM - remote: https://rubygems.org/ - specs: - diff-lcs (1.3) - json (2.1.0) - mini_portile2 (2.4.0) - multi_json (1.14.1) - net-scp (3.0.0) - net-ssh (>= 2.6.5, < 7.0.0) - net-ssh (6.0.2) - net-telnet (0.1.1) - nokogiri (1.10.9) - mini_portile2 (~> 2.4.0) - nokogiri (1.10.9-x64-mingw32) - mini_portile2 (~> 2.4.0) - octopus-serverspec-extensions (0.18.1) - json (~> 2.1.0) - rspec (~> 3.0) - serverspec (~> 2) - specinfra (~> 2) - rake (13.0.1) - rspec (3.9.0) - rspec-core (~> 3.9.0) - rspec-expectations (~> 3.9.0) - rspec-mocks (~> 3.9.0) - rspec-core (3.9.1) - rspec-support (~> 3.9.1) - rspec-expectations (3.9.1) - diff-lcs (>= 1.2.0, < 2.0) - rspec-support (~> 3.9.0) - rspec-its (1.3.0) - rspec-core (>= 3.0.0) - rspec-expectations (>= 3.0.0) - rspec-mocks (3.9.1) - diff-lcs (>= 1.2.0, < 2.0) - rspec-support (~> 3.9.0) - rspec-support (3.9.2) - rspec-teamcity (0.0.1) - rspec (>= 2.99, >= 2.14.2, < 4) - serverspec (2.41.5) - multi_json - rspec (~> 3.0) - rspec-its - specinfra (~> 2.72) - sfl (2.3) - specinfra (2.82.16) - net-scp - net-ssh (>= 2.7) - net-telnet (= 0.1.1) - sfl - -PLATFORMS - ruby - x64-mingw32 - -DEPENDENCIES - nokogiri - octopus-serverspec-extensions (~> 0.18.1) - rake - rspec-teamcity (~> 0.0.1) - serverspec - -BUNDLED WITH - 1.17.2 diff --git a/E2ETests/Rakefile b/E2ETests/Rakefile deleted file mode 100644 index 65a199af5..000000000 --- a/E2ETests/Rakefile +++ /dev/null @@ -1,6 +0,0 @@ -require 'rake' -require 'rspec/core/rake_task' - -RSpec::Core::RakeTask.new(:spec) do |t| - t.pattern = 'spec/*_spec.rb' -end diff --git a/E2ETests/Scenarios/Server_Scenario_01_Install.ps1 b/E2ETests/Scenarios/Server_Scenario_01_Install.ps1 index 7569a238f..8e424147d 100644 --- a/E2ETests/Scenarios/Server_Scenario_01_Install.ps1 +++ b/E2ETests/Scenarios/Server_Scenario_01_Install.ps1 @@ -118,11 +118,12 @@ Configuration Server_Scenario_01_Install $user = $repository.Users.GetCurrent() $createApiKeyResult = $repository.Users.CreateApiKey($user, "Octopus DSC Testing") - #save it to enviornment variables for tests to use - [environment]::SetEnvironmentVariable("OctopusServerUrl", "http://localhost:81", "User") - [environment]::SetEnvironmentVariable("OctopusServerUrl", "http://localhost:81", "Machine") - [environment]::SetEnvironmentVariable("OctopusApiKey", $createApiKeyResult.ApiKey, "User") - [environment]::SetEnvironmentVariable("OctopusApiKey", $createApiKeyResult.ApiKey, "Machine") + #save it to file for tests to use + $content = @{ + "OctopusServerUrl" = "http://localhost:81"; + "OctopusApiKey" = $createApiKeyResult.ApiKey; + } + set-content "c:\temp\octopus-configured.marker" ($content | ConvertTo-Json) } TestScript = { Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Newtonsoft.Json.dll" diff --git a/E2ETests/Scenarios/Server_Scenario_07_Reinstall.ps1 b/E2ETests/Scenarios/Server_Scenario_07_Reinstall.ps1 index 9a86c5648..dad7d80a3 100644 --- a/E2ETests/Scenarios/Server_Scenario_07_Reinstall.ps1 +++ b/E2ETests/Scenarios/Server_Scenario_07_Reinstall.ps1 @@ -97,11 +97,12 @@ Configuration Server_Scenario_07_Reinstall write-verbose "setting OctopusApiKey to $($createApiKeyResult.ApiKey)" - #save it to enviornment variables for tests to use - [environment]::SetEnvironmentVariable("OctopusServerUrl", "http://localhost:81", "User") - [environment]::SetEnvironmentVariable("OctopusServerUrl", "http://localhost:81", "Machine") - [environment]::SetEnvironmentVariable("OctopusApiKey", $createApiKeyResult.ApiKey, "User") - [environment]::SetEnvironmentVariable("OctopusApiKey", $createApiKeyResult.ApiKey, "Machine") + #save it to file for tests to use + $content = @{ + "OctopusServerUrl" = "http://localhost:81"; + "OctopusApiKey" = $createApiKeyResult.ApiKey; + } + set-content "c:\temp\octopus-configured.marker" ($content | ConvertTo-Json) } TestScript = { Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Newtonsoft.Json.dll" diff --git a/E2ETests/Spec/TestHelpers/Get-EnvironmentDetails.ps1 b/E2ETests/Spec/TestHelpers/Get-EnvironmentDetails.ps1 new file mode 100644 index 000000000..6d35850a3 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Get-EnvironmentDetails.ps1 @@ -0,0 +1,29 @@ +function Get-EnvironmentDetails { + [CmdletBinding()] + [OutputType([HashTable])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $EnvironmentName, + [Parameter(Mandatory=$false)] + [string] + $SpaceId + ) + + $serverSupportsSpaces = Test-ServerSupportsSpaces $OctopusServerUrl + if ($serverSupportsSpaces -and (-not [string]::IsNullOrEmpty($SpaceId))) { + $spaceFragment = "$SpaceId/" + } + + [PSCustomObject]$environment = Get-EnvironmentViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -EnvironmentName $EnvironmentName -SpaceFragment $spaceFragment + + return @{ + Exists = $null -ne $environment; + } +} diff --git a/E2ETests/Spec/TestHelpers/Get-SpaceDetails.ps1 b/E2ETests/Spec/TestHelpers/Get-SpaceDetails.ps1 new file mode 100644 index 000000000..17f0538ec --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Get-SpaceDetails.ps1 @@ -0,0 +1,26 @@ +function Get-SpaceDetails { + [CmdletBinding()] + [OutputType([HashTable])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $SpaceName + ) + + [PSCustomObject]$space = Get-SpaceViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -SpaceName $SpaceName + $exists = $null -ne $space + $description = "" + if ($exists) { + $description = $space.Description + } + return @{ + Exists = $exists; + Description = $description; + } +} diff --git a/E2ETests/Spec/TestHelpers/Get-TentacleDetails.ps1 b/E2ETests/Spec/TestHelpers/Get-TentacleDetails.ps1 new file mode 100644 index 000000000..b40b93e28 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Get-TentacleDetails.ps1 @@ -0,0 +1,56 @@ +function Get-TentacleDetails { + [CmdletBinding()] + [OutputType([HashTable])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $InstanceName, + [Parameter(Mandatory=$false)] + [string] + $SpaceId + ) + + [bool]$exists = Test-Path "c:\program files\Octopus Deploy\Tentacle\Tentacle.exe" + [PSCustomObject]$machine = @{} + [string[]]$environments = @() + [string[]]$tenants = @() + [string]$machinePolicy = $null + [bool]$isOnline = $false + [string]$communicationStyle = $Null + + if ($exists) { + $thumbprint = Get-Thumbprint $InstanceName + $serverSupportsSpaces = Test-ServerSupportsSpaces $OctopusServerUrl + if ($serverSupportsSpaces -and (-not [string]::IsNullOrEmpty($SpaceId))) { + $spaceFragment = "$SpaceId/" + } + $machine = Get-MachineViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -Thumbprint $thumbprint -SpaceFragment $spaceFragment + $communicationStyle = $machine.Endpoint.CommunicationStyle + $environments = (Get-Environments -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -SpaceFragment $spaceFragment) | Where-Object { $machine.EnvironmentIds -contains $_.Id } | Select-Object -ExpandProperty Name + $tenants = (Get-Tenants -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -SpaceFragment $spaceFragment) | Where-Object { $machine.TenantIds -contains $_.Id } | Select-Object -ExpandProperty Name + $machinePolicy = (Get-MachinePolicies -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -SpaceFragment $spaceFragment) | Where-Object { $machine.MachinePolicyId -contains $_.Id } | Select-Object -ExpandProperty Name + $isOnline = Test-IsTentacleOnline -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -SpaceFragment $spaceFragment + } + + return @{ + Exists = $exists; + IsRegisteredWithTheServer = $null -ne $machine; + IsOnline = $isOnline + IsListening = $communicationStyle -eq "TentaclePassive" + IsPolling = $communicationStyle -eq "TentacleActive" + Environments = $environments + Roles = $machine.Roles + DisplayName = $machine.Name + Tenants = $tenants + TenantTags = $machine.TenantTags + Policy = $machinePolicy + TenantedDeploymentParticipation = $machine.TenantedDeploymentParticipation + Endpoint = $machine.Uri + } +} diff --git a/E2ETests/Spec/TestHelpers/Get-WorkerDetails.ps1 b/E2ETests/Spec/TestHelpers/Get-WorkerDetails.ps1 new file mode 100644 index 000000000..39b23ebe7 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Get-WorkerDetails.ps1 @@ -0,0 +1,43 @@ +function Get-WorkerDetails { + [CmdletBinding()] + [OutputType([HashTable])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $InstanceName, + [Parameter(Mandatory=$false)] + [string] + $SpaceId + ) + + [bool]$exists = Test-Path "c:\program files\Octopus Deploy\Tentacle\Tentacle.exe" + [PSCustomObject]$worker = @{} + [bool]$isOnline = $false + [string]$communicationStyle = $Null + + if ($exists) { + $thumbprint = Get-Thumbprint $InstanceName + $serverSupportsSpaces = Test-ServerSupportsSpaces $OctopusServerUrl + if ($serverSupportsSpaces -and (-not [string]::IsNullOrEmpty($SpaceId))) { + $spaceFragment = "$SpaceId/" + } + $worker = Get-WorkerViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -Thumbprint $thumbprint -SpaceFragment $spaceFragment + $communicationStyle = $worker.Endpoint.CommunicationStyle + $isOnline = Test-IsWorkerOnline -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -SpaceFragment $spaceFragment + } + + return @{ + Exists = $exists; + IsRegisteredWithTheServer = $null -ne $worker; + IsOnline = $isOnline + IsListening = $communicationStyle -eq "TentaclePassive" + IsPolling = $communicationStyle -eq "TentacleActive" + DisplayName = $worker.Name + } +} diff --git a/E2ETests/Spec/TestHelpers/Get-WorkerPoolDetails.ps1 b/E2ETests/Spec/TestHelpers/Get-WorkerPoolDetails.ps1 new file mode 100644 index 000000000..a03eb7875 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Get-WorkerPoolDetails.ps1 @@ -0,0 +1,29 @@ +function Get-WorkerPoolDetails { + [CmdletBinding()] + [OutputType([HashTable])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $WorkerPoolName, + [Parameter(Mandatory=$false)] + [string] + $SpaceId + ) + + $serverSupportsSpaces = Test-ServerSupportsSpaces $OctopusServerUrl + if ($serverSupportsSpaces -and (-not [string]::IsNullOrEmpty($SpaceId))) { + $spaceFragment = "$SpaceId/" + } + + [PSCustomObject]$workerPool = Get-WorkerPoolViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -WorkerPoolName $WorkerPoolName -SpaceFragment $spaceFragment + + return @{ + Exists = $null -ne $workerPool; + } +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-EnvironmentViaApi.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-EnvironmentViaApi.ps1 new file mode 100644 index 000000000..b35cb7bf5 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-EnvironmentViaApi.ps1 @@ -0,0 +1,25 @@ +function Get-EnvironmentViaApi { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $EnvironmentName, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)environments/all?api-key=$OctopusApiKey" + $response = Invoke-RestMethod $url + $environment = $response | Where-Object { $_.Name -eq $EnvironmentName } + + return $environment +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-Environments.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-Environments.ps1 new file mode 100644 index 000000000..8d54935d9 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-Environments.ps1 @@ -0,0 +1,19 @@ +function Get-Environments { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)environments/all?api-key=$OctopusApiKey" + return Invoke-RestMethod $url +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-MachinePolicies.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-MachinePolicies.ps1 new file mode 100644 index 000000000..01780e322 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-MachinePolicies.ps1 @@ -0,0 +1,19 @@ +function Get-MachinePolicies { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)machinepolicies/all?api-key=$OctopusApiKey" + return Invoke-RestMethod $url +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-MachineViaApi.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-MachineViaApi.ps1 new file mode 100644 index 000000000..5f55d0f5f --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-MachineViaApi.ps1 @@ -0,0 +1,25 @@ +function Get-MachineViaApi { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)machines/all?api-key=$OctopusApiKey" + $response = Invoke-RestMethod $url + $machine = $response | Where-Object { $_.Thumbprint -eq $thumbprint } + + return $machine +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-SpaceViaApi.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-SpaceViaApi.ps1 new file mode 100644 index 000000000..382c95091 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-SpaceViaApi.ps1 @@ -0,0 +1,21 @@ +function Get-SpaceViaApi { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $SpaceName + ) + + $url = "$OctopusServerUrl/api/spaces/all?api-key=$OctopusApiKey" + $response = Invoke-RestMethod $url + $space = $response | Where-Object { $_.Name -eq $SpaceName } + + return $space +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-Tenants.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-Tenants.ps1 new file mode 100644 index 000000000..0fc6d8ce4 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-Tenants.ps1 @@ -0,0 +1,19 @@ +function Get-Tenants { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)tenants/all?api-key=$OctopusApiKey" + return Invoke-RestMethod $url +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-Thumbprint.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-Thumbprint.ps1 new file mode 100644 index 000000000..b08ab567a --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-Thumbprint.ps1 @@ -0,0 +1,16 @@ +function Get-Thumbprint { + [CmdletBinding()] + [OutputType([string])] + param ( + [Parameter()] + [string] + $InstanceName + ) + + $thumbprint = & "c:\program files\Octopus Deploy\Tentacle\Tentacle.exe" show-thumbprint --console --nologo --instance $InstanceName + $thumbprint = $thumbprint -replace '==== ShowThumbprintCommand starting ====', '' + $thumbprint = $thumbprint -replace 'The thumbprint of this Tentacle is: ', '' + $thumbprint = $thumbprint -replace '==== ShowThumbprintCommand completed ====', '' + $thumbprint = $thumbprint -replace '==== ShowThumbprintCommand ====', '' + return $thumbprint.Trim() +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-WorkerPoolViaApi.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-WorkerPoolViaApi.ps1 new file mode 100644 index 000000000..17a9b69fe --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-WorkerPoolViaApi.ps1 @@ -0,0 +1,25 @@ +function Get-WorkerPoolViaApi { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $WorkerPoolName, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)workerpools/all?api-key=$OctopusApiKey" + $response = Invoke-RestMethod $url + $workerPool = $response | Where-Object { $_.Name -eq $WorkerPoolName } + + return $workerPool +} diff --git a/E2ETests/Spec/TestHelpers/Private/Get-WorkerViaApi.ps1 b/E2ETests/Spec/TestHelpers/Private/Get-WorkerViaApi.ps1 new file mode 100644 index 000000000..a32eeddd5 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Get-WorkerViaApi.ps1 @@ -0,0 +1,25 @@ +function Get-WorkerViaApi { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $url = "$OctopusServerUrl/api/$($spaceFragment)workers/all?api-key=$OctopusApiKey" + $response = Invoke-RestMethod $url + $worker = $response | Where-Object { $_.Thumbprint -eq $thumbprint } + + return $worker +} diff --git a/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilMachineHasCompletedHealthCheck.ps1 b/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilMachineHasCompletedHealthCheck.ps1 new file mode 100644 index 000000000..4e6051e7f --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilMachineHasCompletedHealthCheck.ps1 @@ -0,0 +1,35 @@ +function Invoke-PollUntilMachineHasCompletedHealthCheck { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $counter = 1 + + do + { + $machine = Get-MachineViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -SpaceFragment $spaceFragment + if ($null -eq $machine) { break } + if ($counter -gt 10) { break } + if ($machine.StatusSummary -ne "This machine was recently added. Please perform a health check.") { break } + Write-Information "Machine health check for $($machine.Name) has not yet completed. Waiting 5 seconds to try again." + $counter++ + Start-Sleep -seconds 5 + } while ($true) + + return $machine +} + diff --git a/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilWorkerHasCompletedHealthCheck copy.ps1 b/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilWorkerHasCompletedHealthCheck copy.ps1 new file mode 100644 index 000000000..9b2f8223b --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Invoke-PollUntilWorkerHasCompletedHealthCheck copy.ps1 @@ -0,0 +1,35 @@ +function Invoke-PollUntilWorkerHasCompletedHealthCheck { + [CmdletBinding()] + [OutputType([PSCustomObject])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $counter = 1 + + do + { + $worker = Get-WorkerViaApi -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -SpaceFragment $spaceFragment + if ($null -eq $worker) { break } + if ($counter -gt 10) { break } + if ($worker.StatusSummary -ne "This machine was recently added. Please perform a health check.") { break } + Write-Information "Machine health check for $($worker.Name) has not yet completed. Waiting 5 seconds to try again." + $counter++ + Start-Sleep -seconds 5 + } while ($true) + + return $worker +} + diff --git a/E2ETests/Spec/TestHelpers/Private/Test-IsTentacleOnline.ps1 b/E2ETests/Spec/TestHelpers/Private/Test-IsTentacleOnline.ps1 new file mode 100644 index 000000000..20acf37e4 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Test-IsTentacleOnline.ps1 @@ -0,0 +1,28 @@ +function Test-IsTentacleOnline { + [CmdletBinding()] + [OutputType([boolean])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $machine = Invoke-PollUntilMachineHasCompletedHealthCheck -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -spaceFragment $spaceFragment + $status = $machine.Status + if ("$status" -eq "") { + $status = $machine.HealthStatus + return $status -eq "Healthy" -or $status -eq "HasWarnings" + } else { + return $status -eq "Online" -or $status -eq "CalamariNeedsUpgrade" -or $status -eq "NeedsUpgrade" + } +} diff --git a/E2ETests/Spec/TestHelpers/Private/Test-IsWorkerOnline.ps1 b/E2ETests/Spec/TestHelpers/Private/Test-IsWorkerOnline.ps1 new file mode 100644 index 000000000..959a1bebe --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Test-IsWorkerOnline.ps1 @@ -0,0 +1,28 @@ +function Test-IsWorkerOnline { + [CmdletBinding()] + [OutputType([boolean])] + param ( + [Parameter(Mandatory=$true)] + [string] + $OctopusServerUrl, + [Parameter(Mandatory=$true)] + [string] + $OctopusApiKey, + [Parameter(Mandatory=$true)] + [string] + $thumbprint, + [Parameter(Mandatory=$true)] + [AllowEmptyString()] + [string] + $spaceFragment + ) + + $worker = Invoke-PollUntilWorkerHasCompletedHealthCheck -OctopusServerUrl $OctopusServerUrl -OctopusApiKey $OctopusApiKey -thumbprint $thumbprint -spaceFragment $spaceFragment + $status = $worker.Status + if ("$status" -eq "") { + $status = $worker.HealthStatus + return $status -eq "Healthy" -or $status -eq "HasWarnings" + } else { + return $status -eq "Online" -or $status -eq "CalamariNeedsUpgrade" -or $status -eq "NeedsUpgrade" + } +} diff --git a/E2ETests/Spec/TestHelpers/Private/Test-ServerSupportsSpaces.ps1 b/E2ETests/Spec/TestHelpers/Private/Test-ServerSupportsSpaces.ps1 new file mode 100644 index 000000000..ae1f9da41 --- /dev/null +++ b/E2ETests/Spec/TestHelpers/Private/Test-ServerSupportsSpaces.ps1 @@ -0,0 +1,13 @@ +function Test-ServerSupportsSpaces { + [CmdletBinding()] + [OutputType([boolean])] + param ( + [Parameter()] + [string] + $OctopusServerUrl + ) + + $response = Invoke-RestMethod "$OctopusServerUrl/api/" + + return [System.Version]::Parse($response.version) -gt [System.Version]::Parse('2019.0.0') +} diff --git a/E2ETests/Spec/server_scenario_01_install.Tests.ps1 b/E2ETests/Spec/server_scenario_01_install.Tests.ps1 new file mode 100644 index 000000000..cd099e930 --- /dev/null +++ b/E2ETests/Spec/server_scenario_01_install.Tests.ps1 @@ -0,0 +1,168 @@ +describe server_scenario_01_install { + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopus" { + Test-Path 'c:/ChezOctopus' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopus/Artifacts" { + Test-Path 'c:/ChezOctopus/Artifacts' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopus/Logs" { + Test-Path 'c:/ChezOctopus/Logs' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopus/TaskLogs" { + Test-Path 'c:/ChezOctopus/TaskLogs' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-OctopusServer.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"Name": "OctopusServer"' + } + + it "should have created the service" { + Get-Service 'OctopusDeploy' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 443" { + (Get-NetTCPConnection -LocalPort 443 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Environment: Production" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $environment = Get-EnvironmentDetails $config.OctopusServerUrl $config.OctopusApiKey "Production" + } + + it "should exist" { + $environment.Exists | Should -be $true + } + } + + describe "Space: Integration Team" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $space = Get-SpaceDetails $config.OctopusServerUrl $config.OctopusApiKey "Integration Team" + } + + it "should exist" { + $space.Exists | Should -be $true + } + + it "should have description 'Description for the Integration Team Space'" { + $space.Description | Should -be 'Description for the Integration Team Space' + } + } + + describe "WorkerPool: Secondary Worker Pool" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $workerPool = Get-WorkerPoolDetails $config.OctopusServerUrl $config.OctopusApiKey "Secondary Worker Pool" + } + + it "should exist" { + $workerPool.Exists | Should -be $true + } + } + + #dsc overall status + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} diff --git a/E2ETests/Spec/server_scenario_01_install_spec.rb b/E2ETests/Spec/server_scenario_01_install_spec.rb deleted file mode 100644 index 4f8a52a05..000000000 --- a/E2ETests/Spec/server_scenario_01_install_spec.rb +++ /dev/null @@ -1,79 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/ChezOctopus') do - it { should be_directory } -end - -describe file('c:/ChezOctopus/Artifacts') do - it { should be_directory } -end - -describe file('c:/ChezOctopus/Logs') do - it { should be_directory } -end - -describe file('c:/ChezOctopus/TaskLogs') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-OctopusServer.config\"/ } - its(:content) { should match /\"Name\": \"OctopusServer\"/ } -end - -describe service('OctopusDeploy') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -describe port(443) do - it { should be_listening.with('tcp') } -end - -#environment -describe octopus_deploy_environment(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], "Production") do - it { should exist } -end - -#space -describe octopus_deploy_space(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], 'Integration Team') do - it { should exist } - it { should have_description('Description for the Integration Team Space') } -end - -#worker pool -describe octopus_deploy_worker_pool(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], "Secondary Worker Pool") do - it { should exist } -end - -#dsc overall status -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_02_install_second_node.Tests.ps1 b/E2ETests/Spec/server_scenario_02_install_second_node.Tests.ps1 new file mode 100644 index 000000000..0606687ad --- /dev/null +++ b/E2ETests/Spec/server_scenario_02_install_second_node.Tests.ps1 @@ -0,0 +1,143 @@ +describe server_scenario_02_install_second_node { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopusSecondNode" { + Test-Path 'c:/ChezOctopusSecondNode' -PathType Container | should -be $true + } + + it "should have created c:/ChezOctopus/Artifacts" { + Test-Path 'c:/ChezOctopus/Artifacts' -PathType Container | should -be $true + } + + it "should not store artifacts under the home directory" { + # they should be pointed at c:/ChezOctopus/ + Test-Path 'c:/ChezOctopusSecondNode/Artifacts' | should -be $false + } + + it "should store logs in the local instance folder" { + # node logs go in the local instance folder + Test-Path 'c:/ChezOctopusSecondNode/Logs' | should -be $true + } + + it "should have created c:/ChezOctopus/TaskLogs" { + Test-Path 'c:/ChezOctopus/TaskLogs' -PathType Container | should -be $true + } + + it "should not store task logs under the home directory" { + # they should be pointed at c:/ChezOctopus/TaskLogs + Test-Path 'c:/ChezOctopusSecondNode/TaskLogs' | should -be $false + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/HANode.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/HANode.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-HANode.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/HANode.config' -raw + $contents | should -match '"Name": "HANode"' + } + + it "should have created the service" { + Get-Service 'OctopusDeploy: HANode' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy: HANode').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy: HANode').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy: HANode'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Environment: Production" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $environment = Get-EnvironmentDetails $config.OctopusServerUrl $config.OctopusApiKey "Production" + } + + it "should exist" { + $environment.Exists | Should -be $true + } + } + + #dsc overall status + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_02_install_second_node_spec.rb b/E2ETests/Spec/server_scenario_02_install_second_node_spec.rb deleted file mode 100644 index 12bde6bd1..000000000 --- a/E2ETests/Spec/server_scenario_02_install_second_node_spec.rb +++ /dev/null @@ -1,82 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/ChezOctopusSecondNode') do - it { should be_directory } -end - -describe file('c:/ChezOctopus/Artifacts') do - it { should be_directory } -end - -describe file('c:/ChezOctopusSecondNode/Artifacts') do - it { should_not be_directory } # they should be pointed at c:/ChezOctopus/ -end - -describe file('c:/ChezOctopusSecondNode/Logs') do # node logs go in the local instance folder - it { should be_directory } -end - -describe file('c:/ChezOctopus/TaskLogs') do - it { should be_directory } -end - -describe file('c:/ChezOctopusSecondNode/TaskLogs') do - it { should_not be_directory } # they should be pointed at c:/ChezOctopus/TaskLogs -end - -# unfortunately, cant test the packages folder at this point - its non determinate when it gets created - -# describe file('c:/ChezOctopus/Packages') do -# it { should be_directory } -# end - -# describe file('c:/ChezOctopusSecondNode/Packages') do -# it { should_not be_directory } # they should be pointed at c:/ChezOctopus/Packages -# end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/HANode.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-HANode.config\"/ } - its(:content) { should match /\"Name\": \"HANode\"/ } -end - -describe service('OctopusDeploy: HANode') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -#environment -describe octopus_deploy_environment(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], "Production") do - it { should exist } -end - -#dsc overall status -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_03_remove.Tests.ps1 b/E2ETests/Spec/server_scenario_03_remove.Tests.ps1 new file mode 100644 index 000000000..3e2b7ff8b --- /dev/null +++ b/E2ETests/Spec/server_scenario_03_remove.Tests.ps1 @@ -0,0 +1,71 @@ +describe server_scenario_03_remove { + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have left the executable there" { + # as there is another instance still on the box - we shouldn't have removed the binaries + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have uninstalled the service" { + (Get-Service 'OctopusDeploy' -ErrorAction SilentlyContinue) | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + it "should not be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 443" { + (Get-NetTCPConnection -LocalPort 443 -ErrorAction SilentlyContinue).State | should -be $null + } +} + diff --git a/E2ETests/Spec/server_scenario_03_remove_spec.rb b/E2ETests/Spec/server_scenario_03_remove_spec.rb deleted file mode 100644 index e02c2869f..000000000 --- a/E2ETests/Spec/server_scenario_03_remove_spec.rb +++ /dev/null @@ -1,41 +0,0 @@ -require 'spec_helper' - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should exist } # as there is another instance still on the box - we shouldn't have removed the binaries -end - -describe service('OctopusDeploy') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -describe port(10943) do - it { should_not be_listening.with('tcp') } -end - -describe port(81) do - it { should_not be_listening.with('tcp') } -end - -describe port(443) do - it { should_not be_listening.with('tcp') } -end - -#todo: confirm whether these should be deleted -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do -# it { should_not exist } -# end - -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -# end diff --git a/E2ETests/Spec/server_scenario_04_remove_second_node.Tests.ps1 b/E2ETests/Spec/server_scenario_04_remove_second_node.Tests.ps1 new file mode 100644 index 000000000..280aadd6e --- /dev/null +++ b/E2ETests/Spec/server_scenario_04_remove_second_node.Tests.ps1 @@ -0,0 +1,68 @@ +describe server_scenario_04_remove_second_node { + + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy: HANode' -ErrorAction SilentlyContinue | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + it "should not be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State | should -be $null + } + +} + diff --git a/E2ETests/Spec/server_scenario_04_remove_second_node_spec.rb b/E2ETests/Spec/server_scenario_04_remove_second_node_spec.rb deleted file mode 100644 index f00d16b5a..000000000 --- a/E2ETests/Spec/server_scenario_04_remove_second_node_spec.rb +++ /dev/null @@ -1,37 +0,0 @@ -require 'spec_helper' - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy: HANode') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -describe port(10943) do - it { should_not be_listening.with('tcp') } -end - -describe port(81) do - it { should_not be_listening.with('tcp') } -end - -#todo: confirm whether these should be deleted -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do -# it { should_not exist } -# end - -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -# end diff --git a/E2ETests/Spec/server_scenario_05_install_custom_instance.Tests.ps1 b/E2ETests/Spec/server_scenario_05_install_custom_instance.Tests.ps1 new file mode 100644 index 000000000..2ed3105c6 --- /dev/null +++ b/E2ETests/Spec/server_scenario_05_install_custom_instance.Tests.ps1 @@ -0,0 +1,100 @@ +describe server_scenario_05_install_custom_instance { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/MyOctopusServer.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/MyOctopusServer.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-MyOctopusServer.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/MyOctopusServer.config' -raw + $contents | should -match '"Name": "MyOctopusServer"' + } + + it "should have created the service" { + Get-Service 'OctopusDeploy: MyOctopusServer' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy: MyOctopusServer').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy: MyOctopusServer').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy: MyOctopusServer'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_05_install_custom_instance_spec.rb b/E2ETests/Spec/server_scenario_05_install_custom_instance_spec.rb deleted file mode 100644 index d00913de2..000000000 --- a/E2ETests/Spec/server_scenario_05_install_custom_instance_spec.rb +++ /dev/null @@ -1,42 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/MyOctopusServer.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-MyOctopusServer.config\"/ } - its(:content) { should match /\"Name\": \"MyOctopusServer\"/ } -end - -describe service('OctopusDeploy: MyOctopusServer') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_06_remove_custom_instance.Tests.ps1 b/E2ETests/Spec/server_scenario_06_remove_custom_instance.Tests.ps1 new file mode 100644 index 000000000..7618d5e94 --- /dev/null +++ b/E2ETests/Spec/server_scenario_06_remove_custom_instance.Tests.ps1 @@ -0,0 +1,68 @@ +describe server_scenario_06_remove_custom_instance { + + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy: MyOctopusServer' -ErrorAction SilentlyContinue | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + it "should not be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State | should -be $null + } + +} + diff --git a/E2ETests/Spec/server_scenario_06_remove_custom_instance_spec.rb b/E2ETests/Spec/server_scenario_06_remove_custom_instance_spec.rb deleted file mode 100644 index c777115ea..000000000 --- a/E2ETests/Spec/server_scenario_06_remove_custom_instance_spec.rb +++ /dev/null @@ -1,37 +0,0 @@ -require 'spec_helper' - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy: MyOctopusServer') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -describe port(10943) do - it { should_not be_listening.with('tcp') } -end - -describe port(81) do - it { should_not be_listening.with('tcp') } -end - -#todo: confirm whether these should be deleted -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do -# it { should_not exist } -# end - -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -# end diff --git a/E2ETests/Spec/server_scenario_07_reinstall.Tests.ps1 b/E2ETests/Spec/server_scenario_07_reinstall.Tests.ps1 new file mode 100644 index 000000000..db987f43f --- /dev/null +++ b/E2ETests/Spec/server_scenario_07_reinstall.Tests.ps1 @@ -0,0 +1,114 @@ +describe server_scenario_07_reinstall { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have installed C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $true + } + + it "should have version 2018.12.1" { + (Get-Item 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe').VersionInfo.FileVersion | should -be '2018.12.1' + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer\OctopusServer' | should -be $true + } + + it "should have set the ConfigurationFilePath" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer\OctopusServer' -Name "ConfigurationFilePath" -ErrorAction SilentlyContinue).ConfigurationFilePath | Should -be "C:\Octopus\OctopusServer-OctopusServer.config" + } + + it "should have created the service" { + Get-Service 'OctopusDeploy' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Environment: UAT 1" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $environment = Get-EnvironmentDetails $config.OctopusServerUrl $config.OctopusApiKey "UAT 1" + } + + it "should exist" { + $environment.Exists | Should -be $true + } + } + + #dsc overall status + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_07_reinstall_spec.rb b/E2ETests/Spec/server_scenario_07_reinstall_spec.rb deleted file mode 100644 index 3210e53ec..000000000 --- a/E2ETests/Spec/server_scenario_07_reinstall_spec.rb +++ /dev/null @@ -1,47 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } - it { should have_version('2018.12.1') } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do - it { should exist } - it { should have_property_value('ConfigurationFilePath', :type_string, 'C:\Octopus\OctopusServer-OctopusServer.config') } -end - -describe service('OctopusDeploy') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -#environment -describe octopus_deploy_environment(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], "UAT 1") do - it { should exist } -end - -#dsc overall status -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_08_upgrade.Tests.ps1 b/E2ETests/Spec/server_scenario_08_upgrade.Tests.ps1 new file mode 100644 index 000000000..bd19262cb --- /dev/null +++ b/E2ETests/Spec/server_scenario_08_upgrade.Tests.ps1 @@ -0,0 +1,121 @@ +describe server_scenario_08_upgrade { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have installed the binary" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $true + } + + it "should have installed a newer version" { + # we should've upgraded past this + (Get-Item 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe').VersionInfo.FileVersion | should -BeGreaterThan [System.Version]::Parse('3.3.24.0') + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-OctopusServer.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"Name": "OctopusServer"' + } + + it "should have created the service" { + Get-Service 'OctopusDeploy' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Environment: UAT 1" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $environment = Get-EnvironmentDetails $config.OctopusServerUrl $config.OctopusApiKey "UAT 1" + } + + it "should not exist" { + $environment.Exists | Should -be $false + } + } + + #dsc overall status + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_08_upgrade_spec.rb b/E2ETests/Spec/server_scenario_08_upgrade_spec.rb deleted file mode 100644 index 118af4b02..000000000 --- a/E2ETests/Spec/server_scenario_08_upgrade_spec.rb +++ /dev/null @@ -1,50 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } - #todo: maybe we should have a matcher "it {should have_version_newer_than('3.3.24.0')}" - it { should_not have_version('3.3.24.0') } # we should've upgraded past this -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-OctopusServer.config\"/ } - its(:content) { should match /\"Name\": \"OctopusServer\"/ } -end - -describe service('OctopusDeploy') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -#environment -describe octopus_deploy_environment(ENV['OctopusServerUrl'], ENV['OctopusApiKey'], "UAT 1") do - it { should_not exist } -end - -#dsc overall status -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_09_watchdog_create.Tests.ps1 b/E2ETests/Spec/server_scenario_09_watchdog_create.Tests.ps1 new file mode 100644 index 000000000..23e509353 --- /dev/null +++ b/E2ETests/Spec/server_scenario_09_watchdog_create.Tests.ps1 @@ -0,0 +1,55 @@ +describe server_scenario_09_watchdog_create { + + it "should have installed the watchdog" { + $ProgressPreference = "SilentlyContinue" + $response = (& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --format json-hierarchical | out-string | ConvertFrom-Json) + $LASTEXITCODE | Should -be 0 + $response.Octopus.Watchdog.Enabled | should -be "True" + $response.Octopus.Watchdog.Interval | should -be "10" + $response.Octopus.Watchdog.Instances | should -be "*" + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_09_watchdog_create_spec.rb b/E2ETests/Spec/server_scenario_09_watchdog_create_spec.rb deleted file mode 100644 index 3e09b71e5..000000000 --- a/E2ETests/Spec/server_scenario_09_watchdog_create_spec.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'spec_helper' - -describe command('$ProgressPreference = "SilentlyContinue"; $response = (& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --format json-hierarchical | out-string | ConvertFrom-Json); write-output "$($response.Octopus.Watchdog.Enabled)|$($response.Octopus.Watchdog.Interval)|$($response.Octopus.Watchdog.Instances)"') do - its(:exit_status) { should eq 0 } - its(:stdout) { should match /True\|10\|\*/ } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_10_watchdog_delete.Tests.ps1 b/E2ETests/Spec/server_scenario_10_watchdog_delete.Tests.ps1 new file mode 100644 index 000000000..dc55adefa --- /dev/null +++ b/E2ETests/Spec/server_scenario_10_watchdog_delete.Tests.ps1 @@ -0,0 +1,53 @@ +describe server_scenario_10_watchdog_delete { + + it "should have disabled the watchdog" { + $ProgressPreference = "SilentlyContinue" + $response = (& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --format json-hierarchical | out-string | ConvertFrom-Json) + $LASTEXITCODE | Should -be 0 + $response.Octopus.Watchdog.Enabled | should -be "False" + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_10_watchdog_delete_spec.rb b/E2ETests/Spec/server_scenario_10_watchdog_delete_spec.rb deleted file mode 100644 index db235053b..000000000 --- a/E2ETests/Spec/server_scenario_10_watchdog_delete_spec.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'spec_helper' - -describe command('$ProgressPreference = "SilentlyContinue"; $response = (& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --format json-hierarchical | out-string | ConvertFrom-Json); write-output "$($response.Octopus.Watchdog.Enabled)"') do - its(:exit_status) { should eq 0 } - its(:stdout) { should match /False/ } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_11_remove.Tests.ps1 b/E2ETests/Spec/server_scenario_11_remove.Tests.ps1 new file mode 100644 index 000000000..0c63aadde --- /dev/null +++ b/E2ETests/Spec/server_scenario_11_remove.Tests.ps1 @@ -0,0 +1,68 @@ +describe server_scenario_11_remove { + + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy' -ErrorAction SilentlyContinue | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + it "should not be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State | should -be $null + } + +} + diff --git a/E2ETests/Spec/server_scenario_11_remove_spec.rb b/E2ETests/Spec/server_scenario_11_remove_spec.rb deleted file mode 100644 index 8471c19a7..000000000 --- a/E2ETests/Spec/server_scenario_11_remove_spec.rb +++ /dev/null @@ -1,37 +0,0 @@ -require 'spec_helper' - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -describe port(10943) do - it { should_not be_listening.with('tcp') } -end - -describe port(81) do - it { should_not be_listening.with('tcp') } -end - -#todo: confirm whether these should be deleted -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do -# it { should_not exist } -# end - -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -# end diff --git a/E2ETests/Spec/server_scenario_12_built_in_worker.Tests.ps1 b/E2ETests/Spec/server_scenario_12_built_in_worker.Tests.ps1 new file mode 100644 index 000000000..c1ea99eb0 --- /dev/null +++ b/E2ETests/Spec/server_scenario_12_built_in_worker.Tests.ps1 @@ -0,0 +1,135 @@ +describe server_scenario_12_built_in_worker { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/Artifacts" { + Test-Path 'c:/Octopus/Artifacts' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/Logs" { + Test-Path 'c:/Octopus/Logs' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/TaskLogs" { + Test-Path 'c:/Octopus/TaskLogs' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-OctopusServer.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' -raw + $contents | should -match '"Name": "OctopusServer"' + } + + it "should have created the OctoSquid user" { + Get-LocalUser 'OctoSquid' -ErrorAction SilentlyContinue | should -not -be $null + } + + it "should have added OctoSquid to the local administrators group" { + (Get-LocalGroupMember "Administrators").Name -contains "$env:COMPUTERNAME\OctoSquid" | should -be $true + } + + it "should have created the OctoMollusc user" { + Get-LocalUser 'OctoMollusc' -ErrorAction SilentlyContinue | should -not -be $null + } + + it "should not have added OctoMollusc to the local administrators group" { + (Get-LocalGroupMember "Administrators").Name -contains "$env:COMPUTERNAME\OctoMollusc" | should -be $false + } + + it "should have created the service" { + Get-Service 'OctopusDeploy' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy'").StartName | should -be '.\OctoSquid' + } + + it "should set the BuiltInWorker.CustomAccountUserName" { + $ProgressPreference = "SilentlyContinue" + $response = (& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --instance OctopusServer --format json-hierarchical | out-string | ConvertFrom-Json) + $LASTEXITCODE | Should -be 0 + $response.Octopus.BuiltInWorker.CustomAccountUserName | Should -be "OctoMollusc" + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_12_built_in_worker_spec.rb b/E2ETests/Spec/server_scenario_12_built_in_worker_spec.rb deleted file mode 100644 index b3b789066..000000000 --- a/E2ETests/Spec/server_scenario_12_built_in_worker_spec.rb +++ /dev/null @@ -1,69 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Octopus/Artifacts') do - it { should be_directory } -end - -describe file('c:/Octopus/Logs') do - it { should be_directory } -end - -describe file('c:/Octopus/TaskLogs') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-OctopusServer.config\"/ } - its(:content) { should match /\"Name\": \"OctopusServer\"/ } -end - -describe user('OctoSquid') do - it { should exist } - it { should belong_to_group('Administrators')} -end - -describe user('OctoMollusc') do - it { should exist } - it { should_not belong_to_group('Administrators')} -end - -describe service('OctopusDeploy') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('.\OctoSquid') } -end - -describe command('& "C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" show-configuration --instance OctopusServer --format xml') do - its(:exit_status) { should eq 0 } - its(:stdout) { should match /OctoMollusc<\/set>/ } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_13_remove.Tests.ps1 b/E2ETests/Spec/server_scenario_13_remove.Tests.ps1 new file mode 100644 index 000000000..e6f0a02e0 --- /dev/null +++ b/E2ETests/Spec/server_scenario_13_remove.Tests.ps1 @@ -0,0 +1,68 @@ +describe server_scenario_13_remove { + + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy' -ErrorAction SilentlyContinue | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + it "should not be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State | should -be $null + } + + it "should not be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State | should -be $null + } + +} + diff --git a/E2ETests/Spec/server_scenario_13_remove_spec.rb b/E2ETests/Spec/server_scenario_13_remove_spec.rb deleted file mode 100644 index 8471c19a7..000000000 --- a/E2ETests/Spec/server_scenario_13_remove_spec.rb +++ /dev/null @@ -1,37 +0,0 @@ -require 'spec_helper' - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -describe port(10943) do - it { should_not be_listening.with('tcp') } -end - -describe port(81) do - it { should_not be_listening.with('tcp') } -end - -#todo: confirm whether these should be deleted -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do -# it { should_not exist } -# end - -# describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -# end diff --git a/E2ETests/Spec/server_scenario_14_install_without_configure.Tests.ps1 b/E2ETests/Spec/server_scenario_14_install_without_configure.Tests.ps1 new file mode 100644 index 000000000..f1ab88d56 --- /dev/null +++ b/E2ETests/Spec/server_scenario_14_install_without_configure.Tests.ps1 @@ -0,0 +1,71 @@ +describe server_scenario_14_install_without_configure { + + # from previous install + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have removed C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy' -ErrorAction SilentlyContinue | should -be $null + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_14_install_without_configure_spec.rb b/E2ETests/Spec/server_scenario_14_install_without_configure_spec.rb deleted file mode 100644 index 224e60261..000000000 --- a/E2ETests/Spec/server_scenario_14_install_without_configure_spec.rb +++ /dev/null @@ -1,33 +0,0 @@ -require 'spec_helper' - -# from previous install -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -#describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer\OctopusServer') do -# it { should_not exist } -#end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/OctopusServer.config') do - it { should_not exist } -end - -describe service('OctopusDeploy') do - it { should_not be_installed } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance.Tests.ps1 b/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance.Tests.ps1 new file mode 100644 index 000000000..4bc9b7bbf --- /dev/null +++ b/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance.Tests.ps1 @@ -0,0 +1,112 @@ +describe server_scenario_15_configure_preinstalled_instance { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/Artifacts" { + Test-Path 'c:/Octopus/Artifacts' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/Logs" { + Test-Path 'c:/Octopus/Logs' -PathType Container | should -be $true + } + + it "should have created c:/Octopus/TaskLogs" { + Test-Path 'c:/Octopus/TaskLogs' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe' -PathType Leaf | should -be $true + } + + it "should have created instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\OctopusServer' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\OctopusServer' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Octopus\" + } + + it "should have created the config file" { + Test-Path 'C:/ProgramData/Octopus/OctopusServer/Instances/ConfigurePreInstalledInstance.config' -PathType Leaf | should -be $true + } + + it "should have set 'ConfigurationFilePath' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/ConfigurePreInstalledInstance.config' -raw + $contents | should -match '"ConfigurationFilePath": "C:\\\\Octopus\\\\OctopusServer-ConfigurePreInstalledInstance.config"' + } + + it "should have set 'Name' in the config file" { + $contents = Get-Content 'C:/ProgramData/Octopus/OctopusServer/Instances/ConfigurePreInstalledInstance.config' -raw + $contents | should -match '"Name": "ConfigurePreInstalledInstance"' + } + + it "should have created the service" { + Get-Service 'OctopusDeploy: ConfigurePreInstalledInstance' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy: ConfigurePreInstalledInstance').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy: ConfigurePreInstalledInstance').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy: ConfigurePreInstalledInstance'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10943" { + (Get-NetTCPConnection -LocalPort 10943 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be listening on port 81" { + (Get-NetTCPConnection -LocalPort 81 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance_spec.rb b/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance_spec.rb deleted file mode 100644 index 7ae27f38b..000000000 --- a/E2ETests/Spec/server_scenario_15_configure_preinstalled_instance_spec.rb +++ /dev/null @@ -1,54 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Octopus/Artifacts') do - it { should be_directory } -end - -describe file('c:/Octopus/Logs') do - it { should be_directory } -end - -describe file('c:/Octopus/TaskLogs') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Octopus/Octopus.Server.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\OctopusServer') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Octopus\\") } -end - -describe file('C:/ProgramData/Octopus/OctopusServer/Instances/ConfigurePreInstalledInstance.config') do - it { should exist } - it { should be_file } - its(:content) { should match /\"ConfigurationFilePath\": \"C:\\\\Octopus\\\\OctopusServer-ConfigurePreInstalledInstance.config\"/ } - its(:content) { should match /\"Name\": \"ConfigurePreInstalledInstance\"/ } -end - -describe service('OctopusDeploy: ConfigurePreInstalledInstance') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10943) do - it { should be_listening.with('tcp') } -end - -describe port(81) do - it { should be_listening.with('tcp') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/spec_helper.rb b/E2ETests/Spec/spec_helper.rb deleted file mode 100644 index 4c12f80de..000000000 --- a/E2ETests/Spec/spec_helper.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'serverspec' -require 'rspec/teamcity' -require 'octopus_serverspec_extensions' - -set :backend, :cmd -set :os, :family => 'windows' - -RSpec.configure do |c| - if (ENV['TEAMCITY_PROJECT_NAME']) then - c.add_formatter Spec::Runner::Formatter::TeamcityFormatter - end -end diff --git a/E2ETests/Spec/tentacle_scenario_01_install.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_01_install.Tests.ps1 new file mode 100644 index 000000000..6bc00e2df --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_01_install.Tests.ps1 @@ -0,0 +1,549 @@ +describe tentacle_scenario_01_install { + + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Applications" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have created C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' -PathType Leaf | should -be $true + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\Tentacle' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Tentacle\" + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances' -PathType Container | should -be $true + } + + describe "ListeningTentacle" { + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: ListeningTentacle'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10933" { + (Get-NetTCPConnection -LocalPort 10933 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: ListeningTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacle" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should have display name 'My Listening Tentacle'" { + $tentacle.DisplayName | should -be 'My Listening Tentacle' + } + + it "should be assigned to tenant 'John'" { + $tentacle.Tenants | should -contain 'John' + } + + it "should have tenant tag 'Hosting/Cloud'" { + $tentacle.TenantTags | should -contain 'Hosting/Cloud' + } + + it "should have policy 'Test Policy'" { + $tentacle.Policy | should -be 'Test Policy' + } + + it "should have tenanted deployment participation set to 'TenantedOrUntenanted'" { + $tentacle.TenantedDeploymentParticipation | should -be 'TenantedOrUntenanted' + } + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/listeningtentacle.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/listeningtentacle.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/listeningtentacle.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\ListeningTentacleHome\ListeningTentacle\Tentacle.config' + } + } + + describe "PollingTentacle" { + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: PollingTentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: PollingTentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: PollingTentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: PollingTentacle'").StartName | should -be 'LocalSystem' + } + + describe "Tentacle: PollingTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "PollingTentacle" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a polling tentacle" { + $tentacle.IsPolling | Should -be $true + } + + it "should be in environment 'Env2'" { + $tentacle.Environments | Should -contain 'Env2' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should have display name '$($ENV:COMPUTERNAME)_PollingTentacle'" { + $tentacle.DisplayName | should -be "$($ENV:COMPUTERNAME)_PollingTentacle" + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/pollingtentacle.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/pollingtentacle.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/pollingtentacle.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\Polling Tentacle Home\PollingTentacle\Tentacle.config' + } + } + } + + Describe "ListeningTentacleWithoutAutoRegister" { + ### listening tentacle (without autoregister, no thumbprint): + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10934" { + (Get-NetTCPConnection -LocalPort 10934 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: ListeningTentacleWithoutAutoRegister" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithoutAutoRegister" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should not be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $false + } + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/listeningtentaclewithoutautoregister.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/listeningtentaclewithoutautoregister.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/listeningtentaclewithoutautoregister.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\ListeningTentacleWithoutAutoRegisterHome\ListeningTentacleWithoutAutoRegister\Tentacle.config' + } + + it "should have created the config file" { + Test-Path 'C:\Octopus\ListeningTentacleWithoutAutoRegisterHome\ListeningTentacleWithoutAutoRegister\Tentacle.config' | should -be $true + } + + it "should not have registered the tentacle with the server" { + $content = Get-Content 'C:\Octopus\ListeningTentacleWithoutAutoRegisterHome\ListeningTentacleWithoutAutoRegister\Tentacle.config' -raw + $content | should -not -match "Tentacle.Communication.TrustedOctopusServers" + } + } + + Describe "ListeningTentacleWithThumbprintWithoutAutoRegister" { + ### listening tentacle (without autoregister, with thumbprint set): + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10935" { + (Get-NetTCPConnection -LocalPort 10935 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithThumbprintWithoutAutoRegister" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should have display name 'ListeningTentacleWithThumbprintWithoutAutoRegister'" { + $tentacle.DisplayName | should -be "ListeningTentacleWithThumbprintWithoutAutoRegister" + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithThumbprintWithoutAutoRegister.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithThumbprintWithoutAutoRegister.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithThumbprintWithoutAutoRegister.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\ListeningTentacleWithThumbprintWithoutAutoRegisterHome\ListeningTentacleWithThumbprintWithoutAutoRegister\Tentacle.config' + } + + it "should have created the config file" { + Test-Path 'C:\Octopus\ListeningTentacleWithThumbprintWithoutAutoRegisterHome\ListeningTentacleWithThumbprintWithoutAutoRegister\Tentacle.config' | should -be $true + } + + it "should have registered the tentacle with the server" { + $content = Get-Content 'C:\Octopus\ListeningTentacleWithThumbprintWithoutAutoRegisterHome\ListeningTentacleWithThumbprintWithoutAutoRegister\Tentacle.config' -raw + $content | should -match "Tentacle.Communication.TrustedOctopusServers" + } + } + + Describe "WorkerTentacle" { + ### worker tentacle + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: WorkerTentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: WorkerTentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: WorkerTentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: WorkerTentacle'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10937" { + (Get-NetTCPConnection -LocalPort 10937 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Worker: WorkerTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $worker = Get-WorkerDetails $config.OctopusServerUrl $config.OctopusApiKey "WorkerTentacle" + } + + it "should exist" { + $worker.Exists | Should -be $true + } + + it "should be registered with the server" { + $worker.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $worker.IsOnline | Should -be $true + } + + it "should be a listening worker" { + $worker.IsListening | Should -be $true + } + + it "should have display name 'My Worker Tentacle'" { + $worker.DisplayName | should -be "My Worker Tentacle" + } + + # TODO check pool membership + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/WorkerTentacle.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/WorkerTentacle.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/WorkerTentacle.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config' + } + + it "should have created C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config" { + Test-Path 'C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config' -PathType Leaf | should -be $true + } + + it "should have registered the tentacle with the server" { + Get-Content 'C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config' -raw | should -match "Tentacle.Communication.TrustedOctopusServers" + } + } + + Describe "ListeningTentacleWithCustomAccount" { + ### listening tentacle with specific service account + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount'").StartName | should -be '.\ServiceUser' + } + + it "should be listening on port 10936" { + (Get-NetTCPConnection -LocalPort 10936 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: ListeningTentacleWithCustomAccount" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithCustomAccount" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should have display name 'ListeningTentacleWithCustomAccount'" { + $tentacle.DisplayName | should -be "ListeningTentacleWithCustomAccount" + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithCustomAccount.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithCustomAccount.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithCustomAccount.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config' + } + + it "should have created C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config" { + Test-Path 'C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config' -PathType Leaf | should -be $true + } + + it "should have registered the tentacle with the server" { + Get-Content 'C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config' -raw | Should -match "Tentacle.Communication.TrustedOctopusServers" + } + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_01_install_spec.rb b/E2ETests/Spec/tentacle_scenario_01_install_spec.rb deleted file mode 100644 index bae2a3704..000000000 --- a/E2ETests/Spec/tentacle_scenario_01_install_spec.rb +++ /dev/null @@ -1,246 +0,0 @@ -require 'spec_helper' -require 'json' - -config = JSON.parse(File.read("c:\\temp\\octopus-configured.marker")) - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should be_file } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Tentacle\\") } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances') do - it { should be_directory } -end - -### listening tentacle: - -describe service('OctopusDeploy Tentacle: ListeningTentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10933) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "ListeningTentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_display_name('My Listening Tentacle') } - it { should have_tenant('John') } - it { should have_tenant_tag('Hosting', 'Cloud') } - it { should have_policy('Test Policy') } - it { should have_tenanted_deployment_participation('TenantedOrUntenanted') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/listeningtentacle.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/listeningtentacle.config') -config_json = JSON.parse(config_file) # add check for nil -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\ListeningTentacleHome\ListeningTentacle\Tentacle.config') } -end - -### polling tentacle: - -describe service('OctopusDeploy Tentacle: PollingTentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "PollingTentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_polling_tentacle } - it { should be_in_environment('Env2') } - it { should have_role('Test-Tentacle') } - it { should have_display_name("#{ENV['COMPUTERNAME']}_PollingTentacle") } - it { should have_policy('Default Machine Policy') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/pollingtentacle.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/pollingtentacle.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\Polling Tentacle Home\PollingTentacle\Tentacle.config') } -end - -### listening tentacle (without autoregister, no thumbprint): - -describe service('OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10934) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "ListeningTentacleWithoutAutoRegister") do - it { should exist } - it { should_not be_registered_with_the_server } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/listeningtentaclewithoutautoregister.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/listeningtentaclewithoutautoregister.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\ListeningTentacleWithoutAutoRegisterHome\ListeningTentacleWithoutAutoRegister\Tentacle.config') } -end - -describe file('C:\Octopus\ListeningTentacleWithoutAutoRegisterHome\ListeningTentacleWithoutAutoRegister\Tentacle.config') do - it { should be_file } - its(:content) { should_not match /Tentacle.Communication.TrustedOctopusServers/} -end - -### listening tentacle (without autoregister, with thumbprint set): - -describe service('OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10935) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "ListeningTentacleWithThumbprintWithoutAutoRegister") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_display_name("ListeningTentacleWithThumbprintWithoutAutoRegister")} - it { should have_policy('Default Machine Policy') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithThumbprintWithoutAutoRegister.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithThumbprintWithoutAutoRegister.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\ListeningTentacleWithThumbprintWithoutAutoRegisterHome\ListeningTentacleWithThumbprintWithoutAutoRegister\Tentacle.config') } -end - -describe file('C:\Octopus\ListeningTentacleWithThumbprintWithoutAutoRegisterHome\ListeningTentacleWithThumbprintWithoutAutoRegister\Tentacle.config') do - it { should be_file } - its(:content) { should match /Tentacle\.Communication\.TrustedOctopusServers.*#{config['OctopusServerThumbprint']}/} -end - -### worker tentacle - -describe service('OctopusDeploy Tentacle: WorkerTentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10937) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_worker(config['OctopusServerUrl'], config['OctopusApiKey'], "WorkerTentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_worker } - it { should have_display_name("My Worker Tentacle")} - # TODO check pool membership -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/WorkerTentacle.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/WorkerTentacle.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config') } -end - -describe file('C:\Octopus\WorkerTentacleHome\WorkerTentacle\Tentacle.config') do - it { should be_file } - its(:content) { should match /Tentacle\.Communication\.TrustedOctopusServers.*#{config['OctopusServerThumbprint']}/} -end - -### listening tentacle with specific service account - -describe service('OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('.\ServiceUser') } -end - -describe port(10936) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "ListeningTentacleWithCustomAccount") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_display_name('ListeningTentacleWithCustomAccount')} - it { should have_policy('Default Machine Policy') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithCustomAccount.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/ListeningTentacleWithCustomAccount.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config') } -end - -describe file('C:\Octopus\ListeningTentacleWithCustomAccountHome\ListeningTentacleWithCustomAccount\Tentacle.config') do - it { should be_file } - its(:content) { should match /Tentacle\.Communication\.TrustedOctopusServers.*#{config['OctopusServerThumbprint']}/} -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_02_remove.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_02_remove.Tests.ps1 new file mode 100644 index 000000000..f71e693fe --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_02_remove.Tests.ps1 @@ -0,0 +1,196 @@ +describe tentacle_scenario_02_remove { + #we deliberately dont cleanup the octopus directory, as it contains logs & config + it "should have left c:/Octopus alone" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have left c:/Applications alone" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' | should -be $false + } + + describe "ListeningTentacle" { + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacle' -ErrorAction SilentlyContinue | should -be $null + } + + # Listening Tentacle + describe "Tentacle: ListeningTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacle" + } + + it "should not exist" { + $tentacle.Exists | Should -be $false + } + } + + it "should not be listening on port 10933" { + (Get-NetTCPConnection -LocalPort 10933 -ErrorAction SilentlyContinue).State | should -be $null + } + } + + describe "PollingTentacle" { + # Polling Tentacle + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: PollingTentacle' -ErrorAction SilentlyContinue | should -be $null + } + + describe "Tentacle: PollingTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "PollingTentacle" + } + + it "should not exist" { + $tentacle.Exists | Should -be $false + } + } + } + + describe "ListeningTentacleWithoutAutoRegister" { + # Listening Tentacle with autoregister disabled + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithoutAutoRegister' -ErrorAction SilentlyContinue | should -be $null + } + + describe "Tentacle: ListeningTentacleWithoutAutoRegister" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithoutAutoRegister" + } + + it "should not exist" { + $tentacle.Exists | Should -be $false + } + } + } + + describe "ListeningTentacleWithThumbprintWithoutAutoRegister" { + # Listening Tentacle with autoregister disabled but thumbprint set + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister' -ErrorAction SilentlyContinue | should -be $null + } + + describe "Tentacle: ListeningTentacleWithThumbprintWithoutAutoRegister" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithThumbprintWithoutAutoRegister" + } + + it "should not exist" { + $tentacle.Exists | Should -be $false + } + } + } + + describe "ListeningTentacleWithCustomAccount" { + # Listening Tentacle with autoregister disabled but thumbprint set + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: ListeningTentacleWithCustomAccount' -ErrorAction SilentlyContinue | should -be $null + } + + describe "Tentacle: ListeningTentacleWithCustomAccount" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "ListeningTentacleWithCustomAccount" + } + + it "should not exist" { + $tentacle.Exists | Should -be $false + } + } + } + + describe "WorkerTentacle" { + # Worker Tentacle + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle: WorkerTentacle' -ErrorAction SilentlyContinue | should -be $null + } + + describe "Worker: WorkerTentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $worker = Get-WorkerDetails $config.OctopusServerUrl $config.OctopusApiKey "WorkerTentacle" + } + + it "should not exist" { + $worker.Exists | Should -be $false + } + } + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } + + #todo: can we check its been removed from the server somehow? +} + diff --git a/E2ETests/Spec/tentacle_scenario_02_remove_spec.rb b/E2ETests/Spec/tentacle_scenario_02_remove_spec.rb deleted file mode 100644 index c725ef624..000000000 --- a/E2ETests/Spec/tentacle_scenario_02_remove_spec.rb +++ /dev/null @@ -1,93 +0,0 @@ -require 'spec_helper' -require 'json' - -config = JSON.parse(File.read("c:\\temp\\octopus-configured.marker")) - -#we deliberately dont cleanup the octopus directory, as it contains logs & config -describe file('c:/Octopus') do - it { should exist } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy Tentacle: ListeningTentacle') do - it { should_not be_installed } -end - -# Listening Tentacle -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "ListeningTentacle") do - it { should_not exist } -end - -describe port(10933) do - it { should_not be_listening.with('tcp') } -end - -# Polling Tentacle -describe service('OctopusDeploy Tentacle: PollingTentacle') do - it { should_not be_installed } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "PollingTentacle") do - it { should_not exist } -end - -# Polling Tentacle -describe service('OctopusDeploy Tentacle: PollingTentacle') do - it { should_not be_installed } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "PollingTentacle") do - it { should_not exist } -end - -# Polling Tentacle with autoregister disabled -describe service('OctopusDeploy Tentacle: PollingTentacleWithoutAutoRegister') do - it { should_not be_installed } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "PollingTentacleWithoutAutoRegister") do - it { should_not exist } -end - -# Polling Tentacle with autoregister disabled but thumbprint set -describe service('OctopusDeploy Tentacle: PollingTentacleWithThumbprintWithoutAutoRegister') do - it { should_not be_installed } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "PollingTentacleWithThumbprintWithoutAutoRegister") do - it { should_not exist } -end - -# Worker Tentacle -describe service('OctopusDeploy Tentacle: WorkerTentacle') do - it { should_not be_installed } -end - -describe octopus_deploy_worker(config['OctopusServerUrl'], config['OctopusApiKey'], "WorkerTentacle") do - it { should_not exist } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end - -#todo: confirm whether these should be deleted -#describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle') do -# it { should_not exist } -#end -# -#describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle\Tentacle') do -# it { should_not exist } -#end - - -#todo: can we check its been removed from the server somehow? diff --git a/E2ETests/Spec/tentacle_scenario_03_reinstall.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_03_reinstall.Tests.ps1 new file mode 100644 index 000000000..8d4a93916 --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_03_reinstall.Tests.ps1 @@ -0,0 +1,147 @@ +describe tentacle_scenario_03_reinstall { + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Applications" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have installed C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' | should -be $true + } + + it "should have version 3.20.0.0" { + (Get-Item 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe').VersionInfo.FileVersion | should -be '3.20.0.0' + } + + + describe "Tentacle" { + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10933" { + (Get-NetTCPConnection -LocalPort 10933 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: Tentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "Tentacle" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\Tentacle' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Tentacle\" + } + + it "should have created instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' | should -be $true + } + + it "should have set the ConfigurationFilePath" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' -Name "ConfigurationFilePath" -ErrorAction SilentlyContinue).ConfigurationFilePath | Should -be "C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config" + } + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_03_reinstall_spec.rb b/E2ETests/Spec/tentacle_scenario_03_reinstall_spec.rb deleted file mode 100644 index fb85d139c..000000000 --- a/E2ETests/Spec/tentacle_scenario_03_reinstall_spec.rb +++ /dev/null @@ -1,54 +0,0 @@ -require 'spec_helper' -require 'json' - -config = JSON.parse(File.read("c:\\temp\\octopus-configured.marker")) - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should be_file } - it { should have_version('3.20.0.0') } -end - -describe service('OctopusDeploy Tentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10933) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "Tentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_policy('Default Machine Policy') } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Tentacle\\") } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle\Tentacle') do - it { should exist } - it { should have_property_value('ConfigurationFilePath', :type_string, 'C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_04_upgrade.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_04_upgrade.Tests.ps1 new file mode 100644 index 000000000..a4f56726e --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_04_upgrade.Tests.ps1 @@ -0,0 +1,157 @@ +describe tentacle_scenario_04_upgrade { + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Applications" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have installed the binary" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' -PathType Leaf | should -be $true + } + + it "should have installed a newer version" { + # we should've upgraded past this + (Get-Item 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe').VersionInfo.FileVersion | should -BeGreaterThan [System.Version]::Parse('3.20.0') + } + + describe "Tentacle" { + + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10933" { + (Get-NetTCPConnection -LocalPort 10933 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: Tentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "Tentacle" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should be online" { + $tentacle.IsOnline | Should -be $true + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\Tentacle' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Tentacle\" + } + + # reg entry sticks around for backwards compat + it "should have kept instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' | should -be $true + } + + it "should have kept the ConfigurationFilePath" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' -Name "ConfigurationFilePath" -ErrorAction SilentlyContinue).ConfigurationFilePath | Should -be "C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config" + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config' + } + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_04_upgrade_spec.rb b/E2ETests/Spec/tentacle_scenario_04_upgrade_spec.rb deleted file mode 100644 index da9242875..000000000 --- a/E2ETests/Spec/tentacle_scenario_04_upgrade_spec.rb +++ /dev/null @@ -1,66 +0,0 @@ -require 'spec_helper' -require 'json' - -config = JSON.parse(File.read("c:\\temp\\octopus-configured.marker")) - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should be_file } - #todo: maybe we should have a matcher "it {should have_version_newer_than('3.3.24.0')}" - it { should_not have_version('3.3.24.0') } # we should've upgraded past this -end - -describe service('OctopusDeploy Tentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10933) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "Tentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_online } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_policy('Default Machine Policy') } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Tentacle\\") } -end - -# reg entry sticks around for backwards compat -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle\Tentacle') do - it { should exist } - it { should have_property_value('ConfigurationFilePath', :type_string, 'C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_05_watchdog_create.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_05_watchdog_create.Tests.ps1 new file mode 100644 index 000000000..6b863b1ae --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_05_watchdog_create.Tests.ps1 @@ -0,0 +1,54 @@ +describe tentacle_scenario_05_watchdog_create { + it "should have installed the watchdog" { + $ProgressPreference = "SilentlyContinue" + $response = (& "C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" show-configuration | out-string | ConvertFrom-Json) + $LASTEXITCODE | Should -be 0 + $response.Octopus.Watchdog.Enabled | should -be "True" + $response.Octopus.Watchdog.Interval | should -be "10" + $response.Octopus.Watchdog.Instances | should -be "*" + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_05_watchdog_create_spec.rb b/E2ETests/Spec/tentacle_scenario_05_watchdog_create_spec.rb deleted file mode 100644 index 5bf55c4f5..000000000 --- a/E2ETests/Spec/tentacle_scenario_05_watchdog_create_spec.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'spec_helper' - -describe command('$ProgressPreference = "SilentlyContinue"; $response = (& "C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" show-configuration | out-string | ConvertFrom-Json); write-output "$($response.Octopus.Watchdog.Enabled)|$($response.Octopus.Watchdog.Interval)|$($response.Octopus.Watchdog.Instances)"') do - its(:exit_status) { should eq 0 } - its(:stdout) { should match /True\|10\|\*/ } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_06_watchdog_delete.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_06_watchdog_delete.Tests.ps1 new file mode 100644 index 000000000..0cc82866c --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_06_watchdog_delete.Tests.ps1 @@ -0,0 +1,52 @@ +describe tentacle_scenario_06_watchdog_delete { + it "should have disabled the watchdog" { + $ProgressPreference = "SilentlyContinue" + $response = (& "C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" show-configuration | out-string | ConvertFrom-Json) + $LASTEXITCODE | Should -be 0 + $response.Octopus.Watchdog.Enabled | should -be "False" + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_06_watchdog_delete_spec.rb b/E2ETests/Spec/tentacle_scenario_06_watchdog_delete_spec.rb deleted file mode 100644 index 071a29b46..000000000 --- a/E2ETests/Spec/tentacle_scenario_06_watchdog_delete_spec.rb +++ /dev/null @@ -1,12 +0,0 @@ -require 'spec_helper' - -describe command('$ProgressPreference = "SilentlyContinue"; $response = (& "C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" show-configuration | out-string | ConvertFrom-Json); write-output "$($response.Octopus.Watchdog.Enabled)"') do - its(:exit_status) { should eq 0 } - its(:stdout) { should match /False/ } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_07_remove.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_07_remove.Tests.ps1 new file mode 100644 index 000000000..0bb576766 --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_07_remove.Tests.ps1 @@ -0,0 +1,67 @@ +describe tentacle_scenario_07_remove { + + it "should have kept c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have kept c:/Applications" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have removed C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' | should -be $false + } + + it "should have uninstalled the service" { + Get-Service 'OctopusDeploy Tentacle' -ErrorAction SilentlyContinue | should -be $null + } + + # should reg entry be deleted? + # should instance file be deleted? + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do + { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do + { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_07_remove_spec.rb b/E2ETests/Spec/tentacle_scenario_07_remove_spec.rb deleted file mode 100644 index 9d46d341d..000000000 --- a/E2ETests/Spec/tentacle_scenario_07_remove_spec.rb +++ /dev/null @@ -1,26 +0,0 @@ -require 'spec_helper' - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should_not exist } -end - -describe service('OctopusDeploy Tentacle') do - it { should_not be_installed } -end - -# should reg entry be deleted? -# should instance file be deleted? - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port.Tests.ps1 b/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port.Tests.ps1 new file mode 100644 index 000000000..924a240c2 --- /dev/null +++ b/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port.Tests.ps1 @@ -0,0 +1,156 @@ +describe tentacle_scenario_08_tentacle_comms_port { + it "should have created c:/Octopus" { + Test-Path 'c:/Octopus' -PathType Container | should -be $true + } + + it "should have created c:/Applications" { + Test-Path 'c:/Applications' -PathType Container | should -be $true + } + + it "should have installed the binary" { + Test-Path 'C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe' -PathType Leaf | should -be $true + } + + describe "Tentacle" { + it "should have created the service" { + Get-Service 'OctopusDeploy Tentacle' | should -not -be $null + } + + it "should have set the service to running" { + (Get-Service 'OctopusDeploy Tentacle').Status | should -be "Running" + } + + it "should have set the service start mode" { + (Get-Service 'OctopusDeploy Tentacle').StartType | should -be 'Automatic' + } + + it "should have set the service runas user" { + (Get-WmiObject Win32_Service -Filter "Name='OctopusDeploy Tentacle'").StartName | should -be 'LocalSystem' + } + + it "should be listening on port 10933" { + (Get-NetTCPConnection -LocalPort 10933 -ErrorAction SilentlyContinue).State -contains "Listen" | should -be $true + } + + describe "Tentacle: Tentacle" { + BeforeAll { + foreach ($import in @(Get-ChildItem -Path $PSScriptRoot\TestHelpers\*.ps1 -recurse)) { + . $import.fullname + } + + $config = Get-Content "c:\temp\octopus-configured.marker" | ConvertFrom-Json + $tentacle = Get-TentacleDetails $config.OctopusServerUrl $config.OctopusApiKey "Tentacle" + } + + it "should exist" { + $tentacle.Exists | Should -be $true + } + + it "should be registered with the server" { + $tentacle.IsRegisteredWithTheServer | Should -be $true + } + + it "should not be online" { + # this tentacle wont actually come online, as this scenario is configuring a tentacle behind a loadbalancer + # which we don't have setup. The main thing we care about here is the endpoint below + $tentacle.IsOnline | Should -be $false + } + + it "should be a listening tentacle" { + $tentacle.IsListening | Should -be $true + } + + it "should be in environment 'The-Env'" { + $tentacle.Environments | Should -contain 'The-Env' + } + + it "should have role 'Test-Tentacle'" { + $tentacle.Roles -contains 'Test-Tentacle' | should -be $true + } + + it "should not be assigned to any tenants" { + $tentacle.Tenants | should -be @() + } + + it "should not have any tenant tags" { + $tentacle.TenantTags | should -be @() + } + + it "should have policy 'Default Machine Policy'" { + $tentacle.Policy | should -be 'Default Machine Policy' + } + + it "should have endpoint" { + $tentacle.Endpoint | should -be "https://$($ENV:COMPUTERNAME):10900/" + } + } + + it "should have created registry entries" { + Test-Path 'HKLM:\Software\Octopus\Tentacle' | should -be $true + } + + it "should have set the InstallLocation" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle' -Name "InstallLocation" -ErrorAction SilentlyContinue).InstallLocation | Should -be "C:\Program Files\Octopus Deploy\Tentacle\" + } + + it "should have created instance registry entry" { + Test-Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' | should -be $true + } + + it "should have set the ConfigurationFilePath" { + (Get-ItemProperty -Path 'HKLM:\Software\Octopus\Tentacle\Tentacle' -Name "ConfigurationFilePath" -ErrorAction SilentlyContinue).ConfigurationFilePath | Should -be "C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config" + } + + it "should have created C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config" { + Test-Path 'C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config' -PathType Leaf | should -be $true + } + + it "should have set ConfigurationFilePath in the config file" { + (Get-Content 'C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config' -raw | ConvertFrom-Json).ConfigurationFilePath | Should -be 'C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config' + } + } + + it "should be able to get dsc configuration" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + + Get-DSCConfiguration -ErrorAction Stop + } + + it "should get true back from Test-DSCConfiguraiton" { + $ProgressPreference = "SilentlyContinue" + $state = "" + do { + $state = (Get-DscLocalConfigurationManager).LCMState + write-verbose "LCM state is $state" + Start-Sleep -Seconds 2 + } while ($state -ne "Idle") + Test-DSCConfiguration -ErrorAction Stop | should -be $true + } + + Describe "Get-DSCConfigurationStatus" { + BeforeDiscovery { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $resourceStates = @($status.ResourcesInDesiredState + $status.ResourcesNotInDesiredState) | where-object { $null -ne $_ } + } + + It "should have succeeded" { + $status = @(Get-DSCConfigurationStatus -ErrorAction Stop -All)[0] + $status.Status | Should -be "Success" + } + + It "should have applied <_.ResourceId> correctly" -ForEach $resourceStates { + $_.InDesiredState | should -be $true + } + + It "should have not received any errors from <_.ResourceId>" -ForEach $resourceStates { + $_.Error | should -be $null + } + } +} + diff --git a/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port_spec.rb b/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port_spec.rb deleted file mode 100644 index b8d5c2dcf..000000000 --- a/E2ETests/Spec/tentacle_scenario_08_tentacle_comms_port_spec.rb +++ /dev/null @@ -1,65 +0,0 @@ -require 'spec_helper' -require 'json' - -config = JSON.parse(File.read("c:\\temp\\octopus-configured.marker")) - -describe file('c:/Octopus') do - it { should be_directory } -end - -describe file('c:/Applications') do - it { should be_directory } -end - -describe file('C:/Program Files/Octopus Deploy/Tentacle/Tentacle.exe') do - it { should be_file } - #todo: maybe we should have a matcher "it {should have_version_newer_than('3.3.24.0')}" - it { should_not have_version('3.3.24.0') } # we should've upgraded past this -end - -describe service('OctopusDeploy Tentacle') do - it { should be_installed } - it { should be_running } - it { should have_start_mode('Automatic') } - it { should run_under_account('LocalSystem') } -end - -describe port(10933) do - it { should be_listening.with('tcp') } -end - -describe octopus_deploy_tentacle(config['OctopusServerUrl'], config['OctopusApiKey'], "Tentacle") do - it { should exist } - it { should be_registered_with_the_server } - it { should be_listening_tentacle } - it { should be_in_environment('The-Env') } - it { should have_role('Test-Tentacle') } - it { should have_policy('Default Machine Policy') } - it { should have_endpoint("https://#{ENV['COMPUTERNAME']}:10900/") } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle') do - it { should exist } - it { should have_property_value('InstallLocation', :type_string, "C:\\Program Files\\Octopus Deploy\\Tentacle\\") } -end - -describe windows_registry_key('HKEY_LOCAL_MACHINE\Software\Octopus\Tentacle\Tentacle') do - it { should exist } - it { should have_property_value('ConfigurationFilePath', :type_string, 'C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config') } -end - -describe file('C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config') do - it { should be_file } -end - -config_file = File.read('C:/ProgramData/Octopus/Tentacle/Instances/Tentacle.config') -config_json = JSON.parse(config_file) -describe config_json['ConfigurationFilePath'] do - it { should eq('C:\Octopus\OctopusTentacleHome\Tentacle\Tentacle.config') } -end - -describe windows_dsc do - it { should be_able_to_get_dsc_configuration } - it { should have_test_dsc_configuration_return_true } - it { should have_dsc_configuration_status_of_success } -end diff --git a/Tests/OctopusDSC.Tests.ps1 b/Tests/OctopusDSC.Tests.ps1 index 746216a11..cc1135a77 100644 --- a/Tests/OctopusDSC.Tests.ps1 +++ b/Tests/OctopusDSC.Tests.ps1 @@ -291,7 +291,7 @@ Describe "OctopusDSC" { $path = Resolve-Path "$PSCommandPath/../../E2ETests/Scenarios" $name = @{label="name";expression={[System.Io.Path]::GetFileNameWithoutExtension($_.Name)}}; $fullName = @{label="fullName";expression={$_.FullName}}; - $specPath = @{label="specPath";expression={"$path/../Spec/$([System.Io.Path]::GetFileNameWithoutExtension($_.Name).ToLower() + '_spec.rb')"}}; + $specPath = @{label="specPath";expression={"$path/../Spec/$([System.Io.Path]::GetFileNameWithoutExtension($_.Name).ToLower() + '.Tests.ps1')"}}; $cases = @(Get-ChildItem $path -Recurse -Filter *.ps1 | Select-Object -Property $name, $fullName, $specPath) | ConvertTo-Hashtable } diff --git a/Tests/configure-octopus-for-tentacle-tests.ps1 b/Tests/configure-octopus-for-tentacle-tests.ps1 index c82b56ba9..2514655b8 100644 --- a/Tests/configure-octopus-for-tentacle-tests.ps1 +++ b/Tests/configure-octopus-for-tentacle-tests.ps1 @@ -8,78 +8,75 @@ $octopusAdminPassword="SuperS3cretPassw0rd!" try { - if (-not (Test-Path "c:\temp\octopus-configured.marker")) { - - Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Newtonsoft.Json.dll" - Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Octopus.Client.dll" - - #connect - $endpoint = new-object Octopus.Client.OctopusServerEndpoint $OctopusURI - $repository = new-object Octopus.Client.OctopusRepository $endpoint - - #sign in - $credentials = New-Object Octopus.Client.Model.LoginCommand - $credentials.Username = $octopusAdminUsername - $credentials.Password = $octopusAdminPassword - $repository.Users.SignIn($credentials) - - #create the api key - $user = $repository.Users.GetCurrent() - $createApiKeyResult = $repository.Users.CreateApiKey($user, "Octopus DSC Testing") - - #create an environment for the tentacles to go into - $environmentEditor = $repository.Environments.CreateOrModify("The-Env") - $environment = $environmentEditor.Instance - $repository.Environments.CreateOrModify("Env2") | Out-Null - - #create a project - $projectGroup = $repository.ProjectGroups.Get("ProjectGroups-1") - if($null -eq $projectGroup) { - throw "Default Project group not found during configuration" - } - - $lifecycle = $repository.Lifecycles.FindByName("Default Lifecycle") - if($null -eq $lifecycle) { - throw "Lifecycle 'Default Lifecycle' not found during configuration" - } - - $projectEditor = $repository.Projects.CreateOrModify("Multi tenant project", $projectGroup, $lifecycle) - $project = $projectEditor.Instance - - # setup tag set - $tagSetEditor = $repository.TagSets.CreateOrModify("Hosting") - $tagSetEditor.AddOrUpdateTag("On premises", "Hosted on site", [Octopus.Client.Model.TagResource+StandardColor]::DarkGreen) | Out-Null - $tagSetEditor.AddOrUpdateTag("Cloud", "Hosted in the cloud", [Octopus.Client.Model.TagResource+StandardColor]::LightBlue) | Out-Null - $tagSetEditor.Save() | Out-Null - $tagSet = $tagSetEditor.Instance - - $tenantEditor = $repository.Tenants.CreateOrModify("John") - $tenantEditor.WithTag($tagSet.Tags[0]) | Out-Null - $tenantEditor.ConnectToProjectAndEnvironments($project, $environment) | Out-Null - - # create a non-default Test Machine Policy w/ defaults - $policyResource = $repository.MachinePolicies.GetTemplate() - $policyResource.Name = "Test Policy" - $policyResource.IsDefault = $false - $policyResource.Description = "Test Machine Policy" - $repository.MachinePolicies.Create($policyResource) | Out-Null - - #ensure we have a worker pool - $repository.WorkerPools.CreateOrModify("Secondary Worker Pool") #| Out-Null - - #ensure we have a cloud region (ie, something without a thumbprint, to catch null thumbprint errors) - $cloudRegionEndpoint = New-Object Octopus.Client.Model.Endpoints.CloudRegionEndpointResource - $repository.Machines.CreateOrModify("My Cloud Region", $cloudRegionEndpoint, @($environment), @("cloud-region")) | Out-Null - - $certificate = Invoke-RestMethod "$OctopusURI/api/configuration/certificates/certificate-global?apikey=$($createApiKeyResult.ApiKey)" - $content = @{ - "OctopusServerUrl" = $OctopusURI; - "OctopusApiKey" = $createApiKeyResult.ApiKey; - "OctopusServerThumbprint" = $certificate.Thumbprint; - } - set-content "c:\temp\octopus-configured.marker" ($content | ConvertTo-Json) - Stop-Transcript + Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Newtonsoft.Json.dll" + Add-Type -Path "${env:ProgramFiles}\Octopus Deploy\Octopus\Octopus.Client.dll" + + #connect + $endpoint = new-object Octopus.Client.OctopusServerEndpoint $OctopusURI + $repository = new-object Octopus.Client.OctopusRepository $endpoint + + #sign in + $credentials = New-Object Octopus.Client.Model.LoginCommand + $credentials.Username = $octopusAdminUsername + $credentials.Password = $octopusAdminPassword + $repository.Users.SignIn($credentials) + + #create the api key + $user = $repository.Users.GetCurrent() + $createApiKeyResult = $repository.Users.CreateApiKey($user, "Octopus DSC Testing") + + #create an environment for the tentacles to go into + $environmentEditor = $repository.Environments.CreateOrModify("The-Env") + $environment = $environmentEditor.Instance + $repository.Environments.CreateOrModify("Env2") | Out-Null + + #create a project + $projectGroup = $repository.ProjectGroups.Get("ProjectGroups-1") + if($null -eq $projectGroup) { + throw "Default Project group not found during configuration" } + + $lifecycle = $repository.Lifecycles.FindByName("Default Lifecycle") + if($null -eq $lifecycle) { + throw "Lifecycle 'Default Lifecycle' not found during configuration" + } + + $projectEditor = $repository.Projects.CreateOrModify("Multi tenant project", $projectGroup, $lifecycle) + $project = $projectEditor.Instance + + # setup tag set + $tagSetEditor = $repository.TagSets.CreateOrModify("Hosting") + $tagSetEditor.AddOrUpdateTag("On premises", "Hosted on site", [Octopus.Client.Model.TagResource+StandardColor]::DarkGreen) | Out-Null + $tagSetEditor.AddOrUpdateTag("Cloud", "Hosted in the cloud", [Octopus.Client.Model.TagResource+StandardColor]::LightBlue) | Out-Null + $tagSetEditor.Save() | Out-Null + $tagSet = $tagSetEditor.Instance + + $tenantEditor = $repository.Tenants.CreateOrModify("John") + $tenantEditor.WithTag($tagSet.Tags[0]) | Out-Null + $tenantEditor.ConnectToProjectAndEnvironments($project, $environment) | Out-Null + + # create a non-default Test Machine Policy w/ defaults + $policyResource = $repository.MachinePolicies.GetTemplate() + $policyResource.Name = "Test Policy" + $policyResource.IsDefault = $false + $policyResource.Description = "Test Machine Policy" + $repository.MachinePolicies.Create($policyResource) | Out-Null + + #ensure we have a worker pool + $repository.WorkerPools.CreateOrModify("Secondary Worker Pool") #| Out-Null + + #ensure we have a cloud region (ie, something without a thumbprint, to catch null thumbprint errors) + $cloudRegionEndpoint = New-Object Octopus.Client.Model.Endpoints.CloudRegionEndpointResource + $repository.Machines.CreateOrModify("My Cloud Region", $cloudRegionEndpoint, @($environment), @("cloud-region")) | Out-Null + + $certificate = Invoke-RestMethod "$OctopusURI/api/configuration/certificates/certificate-global?apikey=$($createApiKeyResult.ApiKey)" + $content = @{ + "OctopusServerUrl" = $OctopusURI; + "OctopusApiKey" = $createApiKeyResult.ApiKey; + "OctopusServerThumbprint" = $certificate.Thumbprint; + } + set-content "c:\temp\octopus-configured.marker" ($content | ConvertTo-Json) + Stop-Transcript } catch { diff --git a/Tests/install-test-dependencies.ps1 b/Tests/install-test-dependencies.ps1 index b0182debf..336ca0f55 100644 --- a/Tests/install-test-dependencies.ps1 +++ b/Tests/install-test-dependencies.ps1 @@ -1,47 +1,6 @@ [System.Net.ServicePointManager]::SecurityProtocol = [System.Net.SecurityProtocolType]::Tls12,[System.Net.SecurityProtocolType]::Tls11,[System.Net.SecurityProtocolType]::Tls -if (-not (Test-Path "c:\ProgramData\Chocolatey")) { - write-output "##teamcity[blockOpened name='Installing Chocolatey']" - - write-output "Installing Chocolatey" - iex ((New-Object System.Net.WebClient).DownloadString('https://chocolatey.org/install.ps1')) - if ($LASTEXITCODE -ne 0) { exit 1 } - - write-output "##teamcity[blockClosed name='Installing Chocolatey']" -} - -if (-not (Test-Path "C:\tools\ruby25")) { - - write-output "##teamcity[blockOpened name='Install Ruby']" - - choco install ruby --allow-empty-checksums --yes --version 2.5.0.1 --no-progress - if ($LASTEXITCODE -ne 0) { exit 1 } - - refreshenv - if ($LASTEXITCODE -ne 0) { exit 1 } - - if (-not (Test-Path "c:\temp")) { - New-Item "C:\temp" -Type Directory | out-null - } - - Invoke-WebRequest "https://rubygems.org/downloads/rubygems-update-2.7.4.gem" -outFile "C:\temp\rubygems-update-2.7.4.gem" - & C:\tools\ruby25\bin\gem.cmd install --local C:\temp\rubygems-update-2.7.4.gem - if ($LASTEXITCODE -ne 0) { exit 1 } - & C:\tools\ruby25\bin\update_rubygems.bat --no-ri --no-rdoc - if ($LASTEXITCODE -ne 0) { exit 1 } - - write-output "##teamcity[blockClosed name='Install Ruby']" - - write-output "##teamcity[blockOpened name='Install ServerSpec']" - - write-output "running 'C:\tools\ruby25\bin\gem.cmd install bundler --version 1.16.1 --no-ri --no-rdoc'" - & C:\tools\ruby25\bin\gem.cmd install bundler --version 1.16.1 --no-ri --no-rdoc --force - if ($LASTEXITCODE -ne 0) { exit 1 } - - write-output "##teamcity[blockClosed name='Install ServerSpec']" -} - write-output "##teamcity[blockOpened name='Configuring SQL Server']" Write-Output "Determining SQL Server service name" @@ -139,13 +98,3 @@ $s.Alter() Restart-Service $serviceName -Force write-output "##teamcity[blockClosed name='Configuring SQL Server']" - -write-output "##teamcity[blockOpened name='Installing gem bundle']" - -Set-Location c:\temp\tests -write-output "installing gem bundle" -& C:\tools\ruby25\bin\bundle.bat _1.16.1_ install --path=vendor -if ($LASTEXITCODE -ne 0) { exit 1 } - -write-output "##teamcity[blockClosed name='Install gem bundle']" - diff --git a/Tests/surface-logs.ps1 b/Tests/surface-logs.ps1 index 346de5ba2..e06969145 100644 --- a/Tests/surface-logs.ps1 +++ b/Tests/surface-logs.ps1 @@ -1,43 +1,3 @@ Write-Host "##teamcity[blockOpened name='LCM Configuration']" Get-DscLocalConfigurationManager Write-Host "##teamcity[blockClosed name='LCM Configuration']" - -$ProgressPreference = "SilentlyContinue" - -Write-Host "##teamcity[blockOpened name='Get-DSCConfigurationStatus']" -try { - $status = Get-DSCConfigurationStatus - write-output "Get-DSCConfigurationStatus succeeded" - write-output "--------------------------------------------------" - write-output "DSCConfigurationStatus:" - write-output "--------------------------------------------------" - $status | format-list | write-output - write-output "--------------------------------------------------" - write-output "ResourcesInDesiredState:" - write-output "--------------------------------------------------" - if ($status.ResourcesInDesiredState.length -eq 0) { - write-output "No resources in desired state" - write-output "--------------------------------------------------" - } else { - $status.ResourcesInDesiredState | foreach-object { - $_ | write-output - write-output "--------------------------------------------------" - } - } - write-output "--------------------------------------------------" - write-output "ResourcesNotInDesiredState:" - write-output "--------------------------------------------------" - if ($status.ResourcesNotInDesiredState.length -eq 0) { - write-output "No resources not in desired state" - write-output "--------------------------------------------------" - } else { - $status.ResourcesNotInDesiredState | foreach-object { - $_ | write-warning - write-output "--------------------------------------------------" - } - } -} catch { - write-output "Get-DSCConfigurationStatus failed" - write-output $_ -} -Write-Host "##teamcity[blockClosed name='Get-DSCConfigurationStatus']" diff --git a/vagrantfile b/vagrantfile index 31bcaea25..0b0899716 100644 --- a/vagrantfile +++ b/vagrantfile @@ -27,10 +27,15 @@ $run_test_scenario_script = <