diff --git a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemotePSSessionHelper.ps1 b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemotePSSessionHelper.ps1 index 3089c798fd..e5c54d21e8 100644 --- a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemotePSSessionHelper.ps1 +++ b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemotePSSessionHelper.ps1 @@ -9,6 +9,9 @@ param( [Parameter(Mandatory=$true)] [string]$accountPassword, + [Parameter(Mandatory=$true)] + [string]$deployedFolderPath, + [Parameter(Mandatory=$false)] [string]$dotnetRuntimePath = "", @@ -43,14 +46,14 @@ if ($serverAction -eq "StartServer") { Write-Host "Starting the application on machine '$serverName'" $startServerScriptPath = "$PSScriptRoot\StartServer.ps1" - $remoteResult=Invoke-Command -Session $psSession -FilePath $startServerScriptPath -ArgumentList $dotnetRuntimePath, $executablePath, $executableParameters, $serverType, $serverName, $applicationBaseUrl, $environmentVariables + $remoteResult=Invoke-Command -Session $psSession -FilePath $startServerScriptPath -ArgumentList $deployedFolderPath, $dotnetRuntimePath, $executablePath, $executableParameters, $serverType, $serverName, $applicationBaseUrl, $environmentVariables } else { Write-Host "Stopping the application on machine '$serverName'" $stopServerScriptPath = "$PSScriptRoot\StopServer.ps1" $serverProcessName = [System.IO.Path]::GetFileNameWithoutExtension($executablePath) - $remoteResult=Invoke-Command -Session $psSession -FilePath $stopServerScriptPath -ArgumentList $serverProcessName, $serverType, $serverName + $remoteResult=Invoke-Command -Session $psSession -FilePath $stopServerScriptPath -ArgumentList $deployedFolderPath, $serverProcessName, $serverType, $serverName } Remove-PSSession $psSession diff --git a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemoteWindowsDeployer.cs b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemoteWindowsDeployer.cs index fcc3e0f4bc..26cf6621a5 100644 --- a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemoteWindowsDeployer.cs +++ b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/RemoteWindowsDeployer.cs @@ -7,6 +7,7 @@ using System.IO; using System.Linq; using System.Reflection; using System.Text; +using System.Xml.Linq; using Microsoft.Extensions.FileProviders; using Microsoft.Extensions.Logging; @@ -82,6 +83,11 @@ namespace Microsoft.AspNetCore.Server.Testing // Publish the app to a local temp folder on the machine where the test is running DotnetPublish(); + if (_deploymentParameters.ServerType == ServerType.IIS) + { + UpdateWebConfig(); + } + var folderId = Guid.NewGuid().ToString(); _deployedFolderPathInFileShare = Path.Combine(_deploymentParameters.RemoteServerFileSharePath, folderId); @@ -140,6 +146,42 @@ namespace Microsoft.AspNetCore.Server.Testing } } + private void UpdateWebConfig() + { + var webConfigFilePath = Path.Combine(_deploymentParameters.PublishedApplicationRootPath, "web.config"); + var webConfig = XDocument.Load(webConfigFilePath); + var aspNetCoreSection = webConfig.Descendants("aspNetCore") + .Single(); + + // if the dotnet runtime path is specified, update the published web.config file to have that path + if (!string.IsNullOrEmpty(_deploymentParameters.DotnetRuntimePath)) + { + aspNetCoreSection.SetAttributeValue( + "processPath", + Path.Combine(_deploymentParameters.DotnetRuntimePath, "dotnet.exe")); + } + + var environmentVariablesSection = aspNetCoreSection.Elements("environmentVariables").FirstOrDefault(); + if (environmentVariablesSection == null) + { + environmentVariablesSection = new XElement("environmentVariables"); + aspNetCoreSection.Add(environmentVariablesSection); + } + + foreach (var envVariablePair in _deploymentParameters.EnvironmentVariables) + { + var environmentVariable = new XElement("environmentVariable"); + environmentVariable.SetAttributeValue("name", envVariablePair.Key); + environmentVariable.SetAttributeValue("value", envVariablePair.Value); + environmentVariablesSection.Add(environmentVariable); + } + + using (var fileStream = File.Open(webConfigFilePath, FileMode.Open)) + { + webConfig.Save(fileStream); + } + } + private void RunScript(string serverAction) { var remotePSSessionHelperScript = _scripts.Value.RemotePSSessionHelper; @@ -162,6 +204,7 @@ namespace Microsoft.AspNetCore.Server.Testing parameterBuilder.Append($" -serverName {_deploymentParameters.ServerName}"); parameterBuilder.Append($" -accountName {_deploymentParameters.ServerAccountName}"); parameterBuilder.Append($" -accountPassword {_deploymentParameters.ServerAccountPassword}"); + parameterBuilder.Append($" -deployedFolderPath {_deployedFolderPathInFileShare}"); if (!string.IsNullOrEmpty(_deploymentParameters.DotnetRuntimePath)) { diff --git a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StartServer.ps1 b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StartServer.ps1 index b3b390ae56..d19b9137a4 100644 --- a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StartServer.ps1 +++ b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StartServer.ps1 @@ -1,5 +1,8 @@ [CmdletBinding()] param( + [Parameter(Mandatory=$true)] + [string]$deployedFolderPath, + [Parameter(Mandatory=$false)] [string]$dotnetRuntimePath, @@ -25,21 +28,6 @@ param( Write-Host "Executing the start server script on machine '$serverName'" -IF (-Not [string]::IsNullOrWhitespace($environmentVariables)) -{ - Write-Host "Setting up environment variables" - foreach ($envVariablePair in $environmentVariables.Split(",")){ - $pair=$envVariablePair.Split("="); - [Environment]::SetEnvironmentVariable($pair[0], $pair[1]) - } -} - -if ($executablePath -eq "dotnet.exe") -{ - Write-Host "Setting the dotnet runtime path to the PATH environment variable" - [Environment]::SetEnvironmentVariable("PATH", "$dotnetRuntimePath") -} - Write-Host "Copying shell32.dll as a temporary workaround for issue https://github.com/dotnet/cli/issues/2967" if ($executablePath -eq "dotnet.exe") { @@ -47,30 +35,53 @@ if ($executablePath -eq "dotnet.exe") } else { - $destinationDir = Split-Path $executablePath - Copy-Item C:\Windows\System32\forwarders\shell32.dll $destinationDir + Copy-Item C:\Windows\System32\forwarders\shell32.dll $deployedFolderPath } -$command = $executablePath + " " + $executableParameters + " --server.urls " + $applicationBaseUrl if ($serverType -eq "IIS") { - throw [System.NotImplementedException] "IIS deployment scenarios not yet implemented." + $publishedDirName=Split-Path $deployedFolderPath -Leaf + Write-Host "Creating IIS website '$publishedDirName' for path '$deployedFolderPath'" + Import-Module IISAdministration + $port=([System.Uri]$applicationBaseUrl).Port + $bindingPort="*:" + $port + ":" + New-IISSite -Name $publishedDirName -BindingInformation $bindingPort -PhysicalPath $deployedFolderPath } -elseif ($serverType -eq "Kestrel") +elseif (($serverType -eq "Kestrel") -or ($serverType -eq "WebListener")) { - $command = $command + " --server Microsoft.AspNetCore.Server.Kestrel" - Write-Host "Executing the command '$command'" - Invoke-Expression $command -} -elseif ($serverType -eq "WebListener") -{ - $command = $command + " --server Microsoft.AspNetCore.Server.WebListener" - Write-Host "Executing the command '$command'" - Invoke-Expression $command + if (-Not [string]::IsNullOrWhitespace($environmentVariables)) + { + Write-Host "Setting up environment variables" + foreach ($envVariablePair in $environmentVariables.Split(",")) + { + $pair=$envVariablePair.Split("="); + [Environment]::SetEnvironmentVariable($pair[0], $pair[1]) + } + } + + if ($executablePath -eq "dotnet.exe") + { + Write-Host "Setting the dotnet runtime path to the PATH environment variable" + [Environment]::SetEnvironmentVariable("PATH", "$dotnetRuntimePath") + } + + $command = $executablePath + " " + $executableParameters + " --server.urls " + $applicationBaseUrl + if ($serverType -eq "Kestrel") + { + $command = $command + " --server Microsoft.AspNetCore.Server.Kestrel" + Write-Host "Executing the command '$command'" + Invoke-Expression $command + } + elseif ($serverType -eq "WebListener") + { + $command = $command + " --server Microsoft.AspNetCore.Server.WebListener" + Write-Host "Executing the command '$command'" + Invoke-Expression $command + } } else { - throw [System.InvalidOperationException] "Server type '$serverType' is not supported." + throw [System.InvalidOperationException] "Server type '$serverType' is not supported." } # NOTE: Make sure this is the last statement in this script as its used to get the exit code of this script diff --git a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StopServer.ps1 b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StopServer.ps1 index dd8e618c96..9b66f883c2 100644 --- a/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StopServer.ps1 +++ b/src/Microsoft.AspNetCore.Server.Testing/Deployers/RemoteWindowsDeployer/StopServer.ps1 @@ -1,5 +1,8 @@ [CmdletBinding()] param( + [Parameter(Mandatory=$true)] + [string]$deployedFolderPath, + [Parameter(Mandatory=$true)] [string]$serverProcessName, @@ -37,22 +40,28 @@ Write-Host "Executing the stop server script on machine '$serverName'" if ($serverType -eq "IIS") { - throw [System.NotImplementedException] "IIS deployment scenarios not yet implemented." + $publishedDirName=Split-Path $deployedFolderPath -Leaf + Write-Host "Stopping the IIS website '$publishedDirName'" + Import-Module IISAdministration + Stop-IISSite -Name $publishedDirName -Confirm:$false + Remove-IISSite -Name $publishedDirName -Confirm:$false + net stop w3svc + net start w3svc } else { - Write-Host "Stopping the process '$serverProcessName'" - $serverProcess=Get-Process -Name "$serverProcessName" + Write-Host "Stopping the process '$serverProcessName'" + $serverProcess=Get-Process -Name "$serverProcessName" - if (DoesCommandExist("taskkill")) - { - # Kill the parent and child processes - & taskkill /pid $serverProcess.Id /t /f - } - else - { - Stop-Process -Id $serverProcess.Id - } + if (DoesCommandExist("taskkill")) + { + # Kill the parent and child processes + & taskkill /pid $serverProcess.Id /t /f + } + else + { + Stop-Process -Id $serverProcess.Id -Force + } } # NOTE: Make sure this is the last statement in this script as its used to get the exit code of this script diff --git a/src/Microsoft.AspNetCore.Server.Testing/project.json b/src/Microsoft.AspNetCore.Server.Testing/project.json index 6e62dd241d..ae685b8e47 100644 --- a/src/Microsoft.AspNetCore.Server.Testing/project.json +++ b/src/Microsoft.AspNetCore.Server.Testing/project.json @@ -43,7 +43,9 @@ "System.Net.Http": "", "System.Runtime": { "type": "build" - } + }, + "System.Xml": "", + "System.Xml.Linq": "" } }, "netstandard1.3": { @@ -56,7 +58,8 @@ "System.Runtime.Extensions": "4.1.0-*", "System.Text.RegularExpressions": "4.1.0-*", "System.Threading": "4.0.11-*", - "System.Threading.Thread": "4.0.0-*" + "System.Threading.Thread": "4.0.0-*", + "System.Xml.XDocument": "4.0.11-*" }, "imports": [ "portable-net45+win8"