Skip to content

Commit

Permalink
azurerm_windows_web_app : fix the issue of incorrect application st…
Browse files Browse the repository at this point in the history
…ack setting after updating the web app without changing the `application_stack` configuration (#23372)

Co-authored-by: jackofallops <[email protected]>
  • Loading branch information
sinbai and jackofallops authored Nov 22, 2023
1 parent 51975fb commit 9b4c519
Show file tree
Hide file tree
Showing 4 changed files with 94 additions and 33 deletions.
70 changes: 44 additions & 26 deletions internal/services/appservice/helpers/windows_web_app_schema.go
Original file line number Diff line number Diff line change
Expand Up @@ -617,34 +617,46 @@ func (s *SiteConfigWindows) ExpandForUpdate(metadata sdk.ResourceMetaData, exist
if metadata.ResourceData.HasChange("site_config.0.application_stack") {
if len(s.ApplicationStack) == 1 {
winAppStack := s.ApplicationStack[0]
if winAppStack.NetFrameworkVersion != "" {
expanded.NetFrameworkVersion = pointer.To(winAppStack.NetFrameworkVersion)
}
if winAppStack.NetCoreVersion != "" {
expanded.NetFrameworkVersion = pointer.To(winAppStack.NetCoreVersion)
if metadata.ResourceData.HasChanges("site_config.0.application_stack.0.dotnet_version", "site_config.0.application_stack.0.dotnet_core_version") {
switch {
case winAppStack.NetFrameworkVersion != "":
expanded.NetFrameworkVersion = pointer.To(winAppStack.NetFrameworkVersion)
case winAppStack.NetCoreVersion != "":
expanded.NetFrameworkVersion = pointer.To(winAppStack.NetCoreVersion)
default:
expanded.NetFrameworkVersion = nil
}
}
if winAppStack.PhpVersion != "" {
if winAppStack.PhpVersion != PhpVersionOff {
expanded.PhpVersion = pointer.To(winAppStack.PhpVersion)
} else {
expanded.PhpVersion = pointer.To("")
if metadata.ResourceData.HasChange("site_config.0.application_stack.0.php_version") {
if winAppStack.PhpVersion != "" {
if winAppStack.PhpVersion != PhpVersionOff {
expanded.PhpVersion = pointer.To(winAppStack.PhpVersion)
} else {
expanded.PhpVersion = pointer.To("")
}
}
}
if winAppStack.PythonVersion != "" || winAppStack.Python {
expanded.PythonVersion = pointer.To(winAppStack.PythonVersion)
}
if winAppStack.JavaVersion != "" {
expanded.JavaVersion = pointer.To(winAppStack.JavaVersion)
switch {
case winAppStack.JavaEmbeddedServer:
expanded.JavaContainer = pointer.To(JavaContainerEmbeddedServer)
expanded.JavaContainerVersion = pointer.To(JavaContainerEmbeddedServerVersion)
case winAppStack.TomcatVersion != "":
expanded.JavaContainer = pointer.To(JavaContainerTomcat)
expanded.JavaContainerVersion = pointer.To(winAppStack.TomcatVersion)
case winAppStack.JavaContainer != "":
expanded.JavaContainer = pointer.To(winAppStack.JavaContainer)
expanded.JavaContainerVersion = pointer.To(winAppStack.JavaContainerVersion)
if metadata.ResourceData.HasChange("site_config.0.application_stack.0.java_version") {
if winAppStack.JavaVersion != "" {
expanded.JavaVersion = pointer.To(winAppStack.JavaVersion)
switch {
case winAppStack.JavaEmbeddedServer:
expanded.JavaContainer = pointer.To(JavaContainerEmbeddedServer)
expanded.JavaContainerVersion = pointer.To(JavaContainerEmbeddedServerVersion)
case winAppStack.TomcatVersion != "":
expanded.JavaContainer = pointer.To(JavaContainerTomcat)
expanded.JavaContainerVersion = pointer.To(winAppStack.TomcatVersion)
case winAppStack.JavaContainer != "":
expanded.JavaContainer = pointer.To(winAppStack.JavaContainer)
expanded.JavaContainerVersion = pointer.To(winAppStack.JavaContainerVersion)
}
} else {
expanded.JavaVersion = nil
expanded.JavaContainer = nil
expanded.JavaContainerVersion = nil
}
}
if !features.FourPointOhBeta() {
Expand Down Expand Up @@ -807,22 +819,28 @@ func (s *SiteConfigWindows) Flatten(appSiteConfig *web.SiteConfig, currentStack
var winAppStack ApplicationStackWindows
if currentStack == CurrentStackDotNetCore {
winAppStack.NetCoreVersion = pointer.From(appSiteConfig.NetFrameworkVersion)
}
if currentStack == CurrentStackDotNet {
} else {
winAppStack.NetFrameworkVersion = pointer.From(appSiteConfig.NetFrameworkVersion)
}

winAppStack.PhpVersion = pointer.From(appSiteConfig.PhpVersion)
if winAppStack.PhpVersion == "" {
winAppStack.PhpVersion = PhpVersionOff
}
winAppStack.PythonVersion = pointer.From(appSiteConfig.PythonVersion) // This _should_ always be `""`
winAppStack.Python = currentStack == CurrentStackPython
winAppStack.JavaVersion = pointer.From(appSiteConfig.JavaVersion)

// we should only set JavaVersion when currentStack is java since the API will return the value of JavaVersion that was once set
if currentStack == "java" {
winAppStack.JavaVersion = pointer.From(appSiteConfig.JavaVersion)
}
switch pointer.From(appSiteConfig.JavaContainer) {
case JavaContainerTomcat:
winAppStack.TomcatVersion = *appSiteConfig.JavaContainerVersion
winAppStack.TomcatVersion = pointer.From(appSiteConfig.JavaContainerVersion)
winAppStack.JavaVersion = pointer.From(appSiteConfig.JavaVersion)
case JavaContainerEmbeddedServer:
winAppStack.JavaEmbeddedServer = true
winAppStack.JavaVersion = pointer.From(appSiteConfig.JavaVersion)
}

s.WindowsFxVersion = pointer.From(appSiteConfig.WindowsFxVersion)
Expand Down
7 changes: 7 additions & 0 deletions internal/services/appservice/windows_web_app_resource.go
Original file line number Diff line number Diff line change
Expand Up @@ -788,6 +788,13 @@ func (r WindowsWebAppResource) Update() sdk.ResourceFunc {
return fmt.Errorf("reading Windows %s: %v", id, err)
}

// Despite being part of the defined `Get` response model, site_config is always nil so we get it explicitly
webAppSiteConfig, err := client.GetConfiguration(ctx, id.ResourceGroup, id.SiteName)
if err != nil {
return fmt.Errorf("reading Site Config for Windows %s: %+v", id, err)
}
existing.SiteConfig = webAppSiteConfig.SiteConfig

var serviceFarmId string
servicePlanChange := false
if existing.SiteProperties.ServerFarmID != nil {
Expand Down
48 changes: 41 additions & 7 deletions internal/services/appservice/windows_web_app_resource_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1019,6 +1019,13 @@ func TestAccWindowsWebApp_updateAppStack(t *testing.T) {
),
},
data.ImportStep(),
{
Config: r.healthCheckUpdate(data, "11"),
Check: acceptance.ComposeTestCheckFunc(
check.That(data.ResourceName).ExistsInAzure(r),
),
},
data.ImportStep(),
{
Config: r.dotNet(data, "v5.0"),
Check: acceptance.ComposeTestCheckFunc(
Expand Down Expand Up @@ -2569,6 +2576,34 @@ resource "azurerm_windows_web_app" "test" {
`, r.baseTemplate(data), data.RandomInteger, javaVersion)
}

//nolint:unparam
func (r WindowsWebAppResource) healthCheckUpdate(data acceptance.TestData, javaVersion string) string {
return fmt.Sprintf(`
provider "azurerm" {
features {}
}
%s
resource "azurerm_windows_web_app" "test" {
name = "acctestWA-%d"
location = azurerm_resource_group.test.location
resource_group_name = azurerm_resource_group.test.name
service_plan_id = azurerm_service_plan.test.id
site_config {
health_check_path = "/health"
health_check_eviction_time_in_min = 5
application_stack {
current_stack = "java"
java_version = "%s"
java_embedded_server_enabled = "true"
}
}
}
`, r.baseTemplate(data), data.RandomInteger, javaVersion)
}

func (r WindowsWebAppResource) javaTomcat(data acceptance.TestData, javaVersion string, tomcatVersion string) string {
return fmt.Sprintf(`
provider "azurerm" {
Expand Down Expand Up @@ -2610,18 +2645,17 @@ resource "azurerm_windows_web_app" "test" {
site_config {
application_stack {
dotnet_version = "%s"
php_version = "%s"
python = "%t"
java_version = "%s"
java_container = "%s"
java_container_version = "%s"
dotnet_version = "%s"
php_version = "%s"
python = "%t"
java_version = "%s"
tomcat_version = "%s"
current_stack = "python"
}
}
}
`, r.baseTemplate(data), data.RandomInteger, "v4.0", "7.4", true, "1.8", "TOMCAT", "9.0")
`, r.baseTemplate(data), data.RandomInteger, "v4.0", "7.4", true, "1.8", "9.0")
}

func (r WindowsWebAppResource) withLogsHttpBlob(data acceptance.TestData) string {
Expand Down
2 changes: 2 additions & 0 deletions website/docs/r/windows_web_app.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,8 @@ An `application_stack` block supports the following:

~> **NOTE:** Whilst this property is Optional omitting it can cause unexpected behaviour, in particular for display of settings in the Azure Portal.

~> **NOTE:** Windows Web apps can configure multiple `app_stack` properties, it is recommended to always configure this `Optional` value and set it to the primary application stack of your app to ensure correct operation of this resource and display the correct metadata in the Azure Portal.

* `docker_image_name` - (Optional) The docker image, including tag, to be used. e.g. `azure-app-service/windows/parkingpage:latest`.

* `docker_registry_url` - (Optional) The URL of the container registry where the `docker_image_name` is located. e.g. `https://index.docker.io` or `https://mcr.microsoft.com`. This value is required with `docker_image_name`.
Expand Down

0 comments on commit 9b4c519

Please sign in to comment.