terraform-provider-azurerm
terraform-provider-azurerm copied to clipboard
changing the `azurerm_postgresql_flexible_server` version from 11 to any other version forces a recreate
Is there an existing issue for this?
- [X] I have searched the existing issues
Community Note
- Please vote on this issue by adding a :thumbsup: reaction to the original issue to help the community and maintainers prioritize this request
- Please do not leave "+1" or "me too" comments, they generate extra noise for issue followers and do not help prioritize the request
- If you are interested in working on this issue or have submitted a pull request, please leave a comment and review the contribution guide to help.
Terraform Version
1.5.7
AzureRM Provider Version
3.94.0 and lower versions seem to be impacted
Affected Resource(s)/Data Source(s)
azurerm_postgresql_flexible_server
Terraform Configuration Files
resource "azurerm_postgresql_flexible_server" "server2" {
name = var.name
location = var.location
resource_group_name = var.resource_group_name
administrator_login = var.administrator_login
administrator_password = var.administrator_password
sku_name = var.sku_name
storage_mb = var.storage_mb
zone = var.zone
version = "11" // eg. changing to "12" or "15" forces a replacement
}
Debug Output/Panic Output
Terraform will perform the following actions:
# azurerm_postgresql_flexible_server.server must be replaced
-/+ resource "azurerm_postgresql_flexible_server" "server" {
~ backup_retention_days = 7 -> (known after apply)
~ fqdn = <redacted> -> (known after apply)
~ id = <redacted> -> (known after apply)
name = "psql-test-ra3h3"
+ private_dns_zone_id = (known after apply)
~ public_network_access_enabled = true -> (known after apply)
~ version = "11" -> "15" # forces replacement
# (8 unchanged attributes hidden)
- authentication {
- active_directory_auth_enabled = false -> null
- password_auth_enabled = true -> null
}
}
Expected Behaviour
Terraform should perform the upgrade on the existing resource without forcing a replacement of the server resource.
Actual Behaviour
Terraform forces a replacement of the server resource and all dependant resources.
Steps to Reproduce
- create the postgresql flexible server resource definition
- run terraform apply to create the postgresql flexible server resource
- change the server version from 11 to 15 within the resource definition
- rerun terraform apply
Important Factoids
No response
References
No response
UPDATE: apparently setting the create_mode variable to "Update" is required in order for Terraform not to replace the server resource.
I would honestly expect that changing the value of the server_version variable would not replace existing resources by default, as performing a server upgrade via the Azure Portal doesn't trigger a replacement of any kind either.
Thanks for raising this issue. Service team confirmed the version of postgresql flexible server should be in-place updated while upgrading "version" and create_mode is "Update".
Below is example:
resource "azurerm_postgresql_flexible_server" "test" {
name = "acctest-fs-test183"
resource_group_name = azurerm_resource_group.test.name
location = azurerm_resource_group.test.location
administrator_login = "_admin_Terraform_123123"
administrator_password = "QAZabx123"
sku_name = "GP_Standard_D2s_v3"
zone = "2"
version = "12"
create_mode = "Update"
}
@neil-yechenwei: Is there a reason the provider doesn't set the create_mode to "Update" automatically if version changes? Unless I'm mistaken, I don't think create_mode can always be set to "Update" especially on first creation. This seems to be very error-prone and a good way to lose data.
Am i understanding correctly that there is currently no way to have a terraform config that will depending on the existence of the server automatically create / upgrade it? (because i need to have create_mode = "Default" for creating the server and create_mode = "Update" for upgrading postgres)
@neil-yechenwei as @tanadeau has mentioned above - the provider should be setting create_mode = "Update" automatically as required, that the API behaves in a weird manner is Terraform's problem, not something that should be pushed onto users.
FWIW this is why we shouldn't necessarily expose CreateMode (and similar) fields in resources, but instead infer it from other fields (e.g. hypothetically if there's a field restore_from_server_id = ".." and that field is populated, we could determine that create_mode = "Restore" rather than create_mode = "Default|Update"). It's a bit late for the places we've already exposed this field, but as mentioned above, this is an API/implementation detail that Terraform should be handling - users just want to update the API version, so we should be sending whatever the API needs to achieve that?
As such, @neil-yechenwei would you be able to send a PR to automatically set the value for CreateMode when updating the server in this instance?
Thanks!
Any updates here?
Please fix this, this is ridiculous. The terraform resource documentation even says this:
* create_mode cannot be changed once it's set since it's a parameter at creation.
Followed by:
* While creating the resource, create_mode cannot be set to Update.
And the property itself says:
Changing this forces a new PostgreSQL Flexible Server to be created.
So we have to set it to Create, then we can't even change the value to Update even if we wanted to do an in place upgrade of the version... This is horrible. Users want to be able to upgrade their instance in place, just like they can do through the portal.
(I'm trying this now though and we can change the value of create_mode without it resulting in a re-create of the instance?! In that case the documentation is wrong. But having to do this is still bad. )
@sleenen I figured it out like a month ago, sorry for not posting the answer immediately.
The (very stupid) idea of this implementation seems to be that you only set the create_mode to Update along with other changes. In our scenario, we tried to first set the create_mode, then tf apply, then update the PostgreSQL version. Only setting the create_mode to update with no other changes however recreates the database. After hours of trying stuff out I just tried to do both at once, and it worked 😆 not sure if this explanation was clear, I don't know how to describe it - very confusing ^^
Thanks @lieberlois , I've tried the same. First time I got a weird internal server error with no more explanation. Second try I got a timeout on the polling and the instance wasn't updated to new version.
@sleenen Thats odd, we managed to upgrade all of our instances from 11 to 16 this way 🤔 oh when did you try this? There was an issue on Microsoft side, this was fixed like 1-2 months ago
Tried it last night and this morning again.
@sleenen We have our next release next week on saturday, I'll notify you if everything worked 👍
@tombuildsstuff @neil-yechenwei any update on this?
Please fix this, this is ridiculous. The terraform resource documentation even says this:
* create_mode cannot be changed once it's set since it's a parameter at creation.
Followed by:
* While creating the resource, create_mode cannot be set to Update.
And the property itself says:
Changing this forces a new PostgreSQL Flexible Server to be created.
So we have to set it to Create, then we can't even change the value to Update even if we wanted to do an in place upgrade of the version... This is horrible. Users want to be able to upgrade their instance in place, just like they can do through the portal.
(I'm trying this now though and we can change the value of create_mode without it resulting in a re-create of the instance?! In that case the documentation is wrong. But having to do this is still bad. )
I was about to create an issue but I found this one. The documentation is highly misleading, confusing and contradicts itself. Relying on the knowledge of existence to change the Terraform configuration makes it dependent on external factors and no longer reproducible.
Looking forward to the change that will set "Update" automatically when the version is updated.
I would also have expected that create_mode could be set to Update from the beginning.
This is also an issue when upgrading a server with create_mode=PointInTimeRestore which is common in a staging environment.
Even if I set create_mode=Update Terraform says it will recreate the database server.
$ terraform --version
Terraform v1.9.5
on linux_amd64
+ provider registry.terraform.io/hashicorp/azurerm v3.116.0
$ terraform apply ...
[...]
-/+ resource "azurerm_postgresql_flexible_server" "psql" {
~ create_mode = "PointInTimeRestore" -> "Update"
~ fqdn = "xxxxxx.postgres.database.azure.com" -> (known after apply)
~ id = "xxxxxx" -> (known after apply)
name = "xxxxxx"
~ point_in_time_restore_time_in_utc = "2024-08-27T07:38:13Z" -> (known after apply)
- source_server_id = "xxxxxx" -> null
~ storage_tier = "P20" -> (known after apply)
~ version = "13" -> "15" # forces replacement
# (14 unchanged attributes hidden)
Seems that we have to rely on click-ops and update the server manually in Azure and just bump the version in tfvars.
Please fix this.
Addition:
I've now tried creating a brand new server with v13 and then trying to upgrade it by only changing the version and setting create_mode="Update" and I still end up with terraform wanting to destroy my existing server.
# module.psql.azurerm_postgresql_flexible_server.psql must be replaced
-/+ resource "azurerm_postgresql_flexible_server" "psql" {
~ create_mode = "Default" -> "Update"
~ fqdn = "xxx.postgres.database.azure.com" -> (known after apply)
~ id = "xxx" -> (known after apply)
name = "psql-jfp-axis-se-dev"
~ storage_tier = "P20" -> (known after apply)
~ version = "13" -> "15" # forces replacement
# (14 unchanged attributes hidden)
This is highly unintuitive and I simply do not understand. I am using AzureRM 4.0.1, I started spinning two postgres flexible servers. All is fine, then i wanted to upgrade PG version from 15 -> 16.
I set the create_mode = "Update" and it does this fine without replacing the entire DB and I was now able to update the Prod server on a General tier but not the dev instance on a burst tier. Now I deleted my dev tier, tore it down to set it up again on PG version 16, but now I can't set the create_mode = "Update" on the dev tier without having to destroy it, at the same time i can't change create_mode away from "Update" because that will tear down my prod environment and i can't spin my dev tier up in "Update" mode 😵💫
Please fix this and do it the right way, this is crucial infastructure.
terraform-provider-azurerm/internal/services/postgres/postgresql_flexible_server_resource.go seems to be the problematic code part 🤔 if no create mode is specified, or not explicitly set to "Update" it will force a recreation. What do the Hashicorp guys say to that?
@sleenen I was also facing the same issue then found out this link
please check if Timescaledb, pgaudit, dblink, orafce, pg_partman, postgres_fdw all these extensions are not present before upgrading via terraform
hi any update on this issue ?
Hi, when will the fix be merged? We need it to have a proper in-place upgrade using Terraform.
I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues. If you have found a problem that seems similar to this, please open a new issue and complete the issue template so we can capture all the details necessary to investigate further.