terraform-provider-cloudflare
terraform-provider-cloudflare copied to clipboard
cloudflare_zero_trust_access_application changes on every apply
Confirmation
- [x] This is a bug with an existing resource and is not a feature request or enhancement. Feature requests should be submitted with Cloudflare Support or your account team.
- [x] I have searched the issue tracker and my issue isn't already found.
- [x] I have replicated my issue using the latest version of the provider and it is still present.
Terraform and Cloudflare provider version
Terraform v1.11.2 on linux_amd64
- provider registry.terraform.io/cloudflare/cloudflare v5.3.0
Affected resource(s)
cloudflare_zero_trust_access_application
Terraform configuration files
terraform {
required_providers {
cloudflare = {
source = "cloudflare/cloudflare"
version = "~> 5.3.0"
}
}
}
resource "cloudflare_zero_trust_access_policy" "app" {
account_id = "xxx"
decision = "allow"
include = [{
saml = {
attribute_name = "group"
attribute_value = "test"
identity_provider_id = "xxx"
}
}]
name = "APP-test"
require = [{
group = {
id = "cde0fd42-4c40-4216-a6ab-884e6d435eba"
} }
]
}
resource "cloudflare_zero_trust_access_application" "app" {
account_id = "xxx"
type = "self_hosted"
allow_authenticate_via_warp = true
allowed_idps = ["xxx"]
app_launcher_visible = true
auto_redirect_to_identity = true
destinations = [
{
type = "private"
uri = "192.168.1.200:3389"
cidr = "192.168.1.200"
port_range = "3389"
},
]
name = "test"
options_preflight_bypass = false
policies = [{
id = cloudflare_zero_trust_access_policy.app.id
precedence = 0
decision = "allow"
}, ]
session_duration = "24h"
}
Link to debug output
https://gist.github.com/per-lind/52f4b57820c16096c0f2187a21021205
Panic output
No response
Expected output
No changes on 2nd apply
Actual output
cloudflare_zero_trust_access_application.app will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "app" { ~ aud = "xxx" -> (known after apply) + cors_headers = (known after apply) ~ created_at = "2025-04-10T08:51:27Z" -> (known after apply) ~ destinations = [ ~ { ~ cidr = "192.168.1.200/32" -> "192.168.1.200" + uri = "192.168.1.200:3389" # (2 unchanged attributes hidden) }, ] + footer_links = (known after apply) id = "8fcffbc5-f3af-406a-8941-2f1ad66a82fb" + landing_page_design = (known after apply) name = "test" + path_cookie_attribute = false ~ policies = [ ~ { + connection_rules = (known after apply) ~ exclude = [] -> (known after apply) id = "ce3de7bb-eb8c-49ab-a570-5e2dd6758b34" ~ include = [ - { - saml = { - attribute_name = "group" -> null - attribute_value = "test" -> null - identity_provider_id = "xxx" -> null } -> null }, ] -> (known after apply) - name = "APP-test" -> null ~ precedence = 1 -> 0 ~ require = [ - { - group = { - id = "cde0fd42-4c40-4216-a6ab-884e6d435eba" -> null } -> null }, ] -> (known after apply) # (1 unchanged attribute hidden) }, ] + saas_app = (known after apply) + scim_config = (known after apply) + skip_app_launcher_login_page = false - tags = [] -> null + target_criteria = (known after apply) ~ updated_at = "2025-04-10T08:52:34Z" -> (known after apply) # (10 unchanged attributes hidden) }
Plan: 0 to add, 1 to change, 0 to destroy.
Steps to reproduce
Create an application with a policy to it terraform apply run a 2nd terraform apply
Additional factoids
This does not happen with version 5.1.0
References
https://github.com/cloudflare/terraform-provider-cloudflare/issues/5370
the reproduction case here is invalid for saml. in terraform are separated with equals signs while saml uses colons. can you confirm the reproduction case here?
I ran into a similar issue with the following resource:
resource "cloudflare_zero_trust_access_application" "test-application" {
account_id = var.primary_account_id
allowed_idps = []
app_launcher_visible = true
destinations = [{
type = "public"
uri = "test-application.${var.primary_zone_name}"
}]
domain = "test-application.${var.primary_zone_name}"
http_only_cookie_attribute = true
logo_url = "https://www.cloudflare.com/img/logo-web-badges/cf-logo-on-white-bg.svg"
name = "Test Application"
policies = [{
# For some reason, passing id or id/precedence doesn't work and triggers {"code":12130,"message":"access.api.error.invalid_request: unrecognized policy decision"}
# id = cloudflare_zero_trust_access_policy.test-policy.id
# precedence = 1
# Pull in policy info manually
decision = cloudflare_zero_trust_access_policy.test-policy.decision
exclude = cloudflare_zero_trust_access_policy.test-policy.exclude
include = cloudflare_zero_trust_access_policy.test-policy.include
name = "${cloudflare_zero_trust_access_policy.test-policy.name} (Non-reusable)"
require = cloudflare_zero_trust_access_policy.test-policy.require
# Attempted to add these to fix the resource update, didn't work:
id = "00000000-1111-4222-3333-444444444444"
precedence = 1
}]
type = "self_hosted"
# Attempted to add these to fix the resource update, didn't work:
options_preflight_bypass = false
self_hosted_domains = ["test-application.${var.primary_zone_name}"]
tags = []
}
There are two issues I ran into: first, I can't find a way to pass an existing policy ID to policies. And then, when passing a per-application policy, I get the update on every apply issue that @per-lind is running into.
Output:
# cloudflare_zero_trust_access_application.test-application will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "test-application" {
~ aud = "000111222moremoremore" -> (known after apply)
+ cors_headers = (known after apply)
~ created_at = "2025-04-11T16:09:46Z" -> (known after apply)
+ footer_links = (known after apply)
id = "00000000-1111-4222-3333-444444444444"
+ landing_page_design = (known after apply)
name = "Test Application"
+ path_cookie_attribute = false
~ policies = [
~ {
+ connection_rules = (known after apply)
id = "00000000-1111-4222-3333-444444444444"
~ include = [
~ {
+ auth_context = (known after apply)
+ auth_method = (known after apply)
+ azure_ad = (known after apply)
+ common_name = (known after apply)
+ device_posture = (known after apply)
+ email_domain = (known after apply)
+ email_list = (known after apply)
+ external_evaluation = (known after apply)
+ geo = (known after apply)
+ github_organization = (known after apply)
+ group = (known after apply)
+ gsuite = (known after apply)
+ ip = (known after apply)
+ ip_list = (known after apply)
+ login_method = (known after apply)
+ okta = (known after apply)
+ saml = (known after apply)
+ service_token = (known after apply)
# (1 unchanged attribute hidden)
},
~ {
+ auth_context = (known after apply)
+ auth_method = (known after apply)
+ azure_ad = (known after apply)
+ common_name = (known after apply)
+ device_posture = (known after apply)
+ email_domain = (known after apply)
+ email_list = (known after apply)
+ external_evaluation = (known after apply)
+ geo = (known after apply)
+ github_organization = (known after apply)
+ group = (known after apply)
+ gsuite = (known after apply)
+ ip = (known after apply)
+ ip_list = (known after apply)
+ login_method = (known after apply)
+ okta = (known after apply)
+ saml = (known after apply)
+ service_token = (known after apply)
# (1 unchanged attribute hidden)
},
]
name = "Test Policy (Non-reusable)"
# (4 unchanged attributes hidden)
},
]
+ saas_app = (known after apply)
+ scim_config = (known after apply)
+ skip_app_launcher_login_page = false
tags = []
+ target_criteria = (known after apply)
~ updated_at = "2025-04-11T16:09:46Z" -> (known after apply)
# (13 unchanged attributes hidden)
}
Some IDs/names updated to be more generic.
@jacobbednarz oh sorry about that (the code does however work). I will update the post
I can't find a way to pass an existing policy ID to
policies
@benmanns Same here, I filed a separate bug for that issue: #5499
I will not re-open the issue but it is same as https://github.com/cloudflare/terraform-provider-cloudflare/issues/5370
and the issue WAS NOT FIXED.
Also, the problem in NOT only with cloudflare_zero_trust_access_application but with:
- cloudflare_zero_trust_access_application
- cloudflare_zero_trust_access_policy
- cloudflare_zero_trust_access_identity_provider
- cloudflare_zero_trust_access_group
- cloudflare_zero_trust_list
and maybe more.
octav@MacBook-Pro-m ~/cloudflare main ● tf apply -auto-approve
cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"]: Refreshing state... [id=f26b2aeb-2b29-41de-cf3be7392ead]
cloudflare_zero_trust_access_group.group["Everyone"]: Refreshing state... [id=587dd4d1-4b7b-4e12-9f07aaa43952]
cloudflare_zero_trust_access_group.group["Developers"]: Refreshing state... [id=771359e1-fb1d-43d8-797a255e78b3]
cloudflare_zero_trust_access_group.group["Admins emails"]: Refreshing state... [id=975f4846-5832-8c21-0c69333a209f]
cloudflare_zero_trust_access_group.group["Nifi operators emails"]: Refreshing state... [id=6f6127e4-499a-8bac-5e21bb580820]
cloudflare_zero_trust_access_group.group["Admins ips"]: Refreshing state... [id=8723aad0-8b14-4f39-c293233fbb6d]
cloudflare_zero_trust_access_policy.policy["Everyone"]: Refreshing state... [id=94a93801-209c-4c36-e8a6cac51d89]
cloudflare_zero_trust_access_policy.policy["Filter by email"]: Refreshing state... [id=6bebb1b4-0da3-a77e-e617d31bde08]
cloudflare_zero_trust_access_policy.policy["Filter by email nifi"]: Refreshing state... [id=47efe264-4c3f-a883-2663da932e70]
cloudflare_zero_trust_access_policy.policy["Filter by ip"]: Refreshing state... [id=ceda7e11-5421-4d49-1e9da73fa590]
cloudflare_zero_trust_access_application.application["Nifi"]: Refreshing state... [id=89153a71-9624-4547-9c984dca96bc]
cloudflare_zero_trust_access_application.application["Name"]: Refreshing state... [id=a14da0c5-b2e2-a396-53a3ccf46684]
OpenTofu used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols:
~ update in-place
OpenTofu will perform the following actions:
# cloudflare_zero_trust_access_application.application["Name"] will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "application" {
- allowed_idps = [] -> null
~ aud = "d82d033e988ef82e45f2e1ba752c5b95e01ffbf80e0ec" -> (known after apply)
+ cors_headers = (known after apply)
~ created_at = "2025-03-25T14:01:01Z" -> (known after apply)
+ footer_links = (known after apply)
id = "a14da0c5-b2e2-a396-53a3ccf46684"
+ landing_page_design = (known after apply)
name = "Name"
+ path_cookie_attribute = false
~ policies = [
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
~ include = [
- {
- group = {
- id = "8723aad0-8b14-4f39-c293233fbb6d" -> null
} -> null
},
- {
- group = {
- id = "771359e1-fb1d-43d8-797a255e78b3" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by ip" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "6bebb1b4-0da3-a77e-e617d31bde08"
~ include = [
- {
- group = {
- id = "975f4846-5832-8c21-0c69333a209f" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by email" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
]
+ saas_app = (known after apply)
+ scim_config = (known after apply)
- self_hosted_domains = [
- "*.example.com",
] -> null
+ skip_app_launcher_login_page = false
- tags = [] -> null
+ target_criteria = (known after apply)
~ updated_at = "2025-04-18T09:47:52Z" -> (known after apply)
# (11 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_application.application["Nifi"] will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "application" {
- allowed_idps = [] -> null
~ aud = "235cc2411ba8b022f70353d1f79cb28edf2e80aa220db077d1b8b5f6d3cee1cf" -> (known after apply)
+ cors_headers = (known after apply)
~ created_at = "2025-03-25T14:01:01Z" -> (known after apply)
+ footer_links = (known after apply)
id = "89153a71-9624-4547-9c984dca96bc"
+ landing_page_design = (known after apply)
name = "Nifi"
+ path_cookie_attribute = false
~ policies = [
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
~ include = [
- {
- group = {
- id = "8723aad0-8b14-4f39-c293233fbb6d" -> null
} -> null
},
- {
- group = {
- id = "771359e1-fb1d-43d8-797a255e78b3" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by ip" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "47efe264-4c3f-a883-2663da932e70"
~ include = [
- {
- group = {
- id = "6f6127e4-499a-8bac-5e21bb580820" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by email nifi" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
]
+ saas_app = (known after apply)
+ scim_config = (known after apply)
- self_hosted_domains = [
- "example.com",
] -> null
+ skip_app_launcher_login_page = false
- tags = [] -> null
+ target_criteria = (known after apply)
~ updated_at = "2025-04-18T09:47:52Z" -> (known after apply)
# (11 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_group.group["Admins ips"] will be updated in-place
~ resource "cloudflare_zero_trust_access_group" "group" {
~ created_at = "2025-03-25T13:30:58Z" -> (known after apply)
id = "8723aad0-8b14-4f39-c293233fbb6d"
~ include = [
~ {
~ ip = {
~ ip = "2a02:2f0f:c00::/64" -> "2a02:2f0f:c00:d4a9:d159:548e:6bbd/64"
}
},
# (5 unchanged elements hidden)
]
name = "Admins ips"
~ require = [] -> (known after apply)
~ updated_at = "2025-04-18T09:47:50Z" -> (known after apply)
# (2 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"] will be updated in-place
~ resource "cloudflare_zero_trust_access_identity_provider" "provider" {
~ config = {
+ client_secret = (sensitive value)
~ redirect_url = "https://example.cloudflareaccess.com/cdn-cgi/access/callback" -> (known after apply)
# (5 unchanged attributes hidden)
}
id = "f26b2aeb-2b29-41de-cf3be7392ead"
name = "Name SSO"
~ scim_config = {
+ scim_base_url = (known after apply)
- seat_deprovision = false -> null
+ secret = (sensitive value)
- user_deprovision = false -> null
# (1 unchanged attribute hidden)
}
# (2 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Everyone"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 0 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "94a93801-209c-4c36-e8a6cac51d89"
+ isolation_required = false
name = "Everyone"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:47:51Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by email"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 1 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "6bebb1b4-0da3-a77e-e617d31bde08"
+ isolation_required = false
name = "Filter by email"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:47:51Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by email nifi"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 1 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "47efe264-4c3f-a883-2663da932e70"
+ isolation_required = false
name = "Filter by email nifi"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:47:51Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by ip"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 2 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
+ isolation_required = false
name = "Filter by ip"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:47:51Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
Plan: 0 to add, 8 to change, 0 to destroy.
cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"]: Modifying... [id=f26b2aeb-2b29-41de-cf3be7392ead]
cloudflare_zero_trust_access_group.group["Admins ips"]: Modifying... [id=8723aad0-8b14-4f39-c293233fbb6d]
cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"]: Modifications complete after 1s [id=f26b2aeb-2b29-41de-cf3be7392ead]
cloudflare_zero_trust_access_group.group["Admins ips"]: Modifications complete after 1s [id=8723aad0-8b14-4f39-c293233fbb6d]
cloudflare_zero_trust_access_policy.policy["Filter by email"]: Modifying... [id=6bebb1b4-0da3-a77e-e617d31bde08]
cloudflare_zero_trust_access_policy.policy["Everyone"]: Modifying... [id=94a93801-209c-4c36-e8a6cac51d89]
cloudflare_zero_trust_access_policy.policy["Filter by email nifi"]: Modifying... [id=47efe264-4c3f-a883-2663da932e70]
cloudflare_zero_trust_access_policy.policy["Filter by ip"]: Modifying... [id=ceda7e11-5421-4d49-1e9da73fa590]
cloudflare_zero_trust_access_policy.policy["Everyone"]: Modifications complete after 1s [id=94a93801-209c-4c36-e8a6cac51d89]
cloudflare_zero_trust_access_policy.policy["Filter by ip"]: Modifications complete after 1s [id=ceda7e11-5421-4d49-1e9da73fa590]
cloudflare_zero_trust_access_policy.policy["Filter by email nifi"]: Modifications complete after 1s [id=47efe264-4c3f-a883-2663da932e70]
cloudflare_zero_trust_access_policy.policy["Filter by email"]: Modifications complete after 1s [id=6bebb1b4-0da3-a77e-e617d31bde08]
cloudflare_zero_trust_access_application.application["Nifi"]: Modifying... [id=89153a71-9624-4547-9c984dca96bc]
cloudflare_zero_trust_access_application.application["Name"]: Modifying... [id=a14da0c5-b2e2-a396-53a3ccf46684]
cloudflare_zero_trust_access_application.application["Nifi"]: Modifications complete after 1s [id=89153a71-9624-4547-9c984dca96bc]
cloudflare_zero_trust_access_application.application["Name"]: Modifications complete after 1s [id=a14da0c5-b2e2-a396-53a3ccf46684]
Releasing state lock. This may take a few moments...
Apply complete! Resources: 0 added, 8 changed, 0 destroyed.
###################################################################
octav@MacBook-Pro-m ~/cloudflare main ● tf plan
Acquiring state lock. This may take a few moments...
cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"]: Refreshing state... [id=f26b2aeb-2b29-41de-cf3be7392ead]
cloudflare_zero_trust_access_group.group["Everyone"]: Refreshing state... [id=587dd4d1-4b7b-4e12-9f07aaa43952]
cloudflare_zero_trust_access_group.group["Admins emails"]: Refreshing state... [id=975f4846-5832-8c21-0c69333a209f]
cloudflare_zero_trust_access_group.group["Nifi operators emails"]: Refreshing state... [id=6f6127e4-499a-8bac-5e21bb580820]
cloudflare_zero_trust_access_group.group["Developers"]: Refreshing state... [id=771359e1-fb1d-43d8-797a255e78b3]
cloudflare_zero_trust_access_group.group["Admins ips"]: Refreshing state... [id=8723aad0-8b14-4f39-c293233fbb6d]
cloudflare_zero_trust_access_policy.policy["Everyone"]: Refreshing state... [id=94a93801-209c-4c36-e8a6cac51d89]
cloudflare_zero_trust_access_policy.policy["Filter by email"]: Refreshing state... [id=6bebb1b4-0da3-a77e-e617d31bde08]
cloudflare_zero_trust_access_policy.policy["Filter by email nifi"]: Refreshing state... [id=47efe264-4c3f-a883-2663da932e70]
cloudflare_zero_trust_access_policy.policy["Filter by ip"]: Refreshing state... [id=ceda7e11-5421-4d49-1e9da73fa590]
cloudflare_zero_trust_access_application.application["Name"]: Refreshing state... [id=a14da0c5-b2e2-a396-53a3ccf46684]
cloudflare_zero_trust_access_application.application["Nifi"]: Refreshing state... [id=89153a71-9624-4547-9c984dca96bc]
OpenTofu used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols:
~ update in-place
OpenTofu will perform the following actions:
# cloudflare_zero_trust_access_application.application["Name"] will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "application" {
- allowed_idps = [] -> null
~ aud = "d82d033e988ef82e45f2e17729469889d5f95e01ffbf80e0ec" -> (known after apply)
+ cors_headers = (known after apply)
~ created_at = "2025-03-25T14:01:01Z" -> (known after apply)
+ footer_links = (known after apply)
id = "a14da0c5-b2e2-a396-53a3ccf46684"
+ landing_page_design = (known after apply)
name = "Name"
+ path_cookie_attribute = false
~ policies = [
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
~ include = [
- {
- group = {
- id = "8723aad0-8b14-4f39-c293233fbb6d" -> null
} -> null
},
- {
- group = {
- id = "771359e1-fb1d-43d8-797a255e78b3" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by ip" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "6bebb1b4-0da3-a77e-e617d31bde08"
~ include = [
- {
- group = {
- id = "975f4846-5832-8c21-0c69333a209f" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by email" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
]
+ saas_app = (known after apply)
+ scim_config = (known after apply)
- self_hosted_domains = [
- "*.example.com",
] -> null
+ skip_app_launcher_login_page = false
- tags = [] -> null
+ target_criteria = (known after apply)
~ updated_at = "2025-04-18T09:52:57Z" -> (known after apply)
# (11 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_application.application["Nifi"] will be updated in-place
~ resource "cloudflare_zero_trust_access_application" "application" {
- allowed_idps = [] -> null
~ aud = "235cc2411ba8b022f70353d80aa220db077d1b8b5f6d3cee1cf" -> (known after apply)
+ cors_headers = (known after apply)
~ created_at = "2025-03-25T14:01:01Z" -> (known after apply)
+ footer_links = (known after apply)
id = "89153a71-9624-4547-9c984dca96bc"
+ landing_page_design = (known after apply)
name = "Nifi"
+ path_cookie_attribute = false
~ policies = [
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
~ include = [
- {
- group = {
- id = "8723aad0-8b14-4f39-c293233fbb6d" -> null
} -> null
},
- {
- group = {
- id = "771359e1-fb1d-43d8-797a255e78b3" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by ip" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
~ {
+ connection_rules = (known after apply)
~ exclude = [] -> (known after apply)
id = "47efe264-4c3f-a883-2663da932e70"
~ include = [
- {
- group = {
- id = "6f6127e4-499a-8bac-5e21bb580820" -> null
} -> null
},
] -> (known after apply)
- name = "Filter by email nifi" -> null
~ require = [] -> (known after apply)
# (2 unchanged attributes hidden)
},
]
+ saas_app = (known after apply)
+ scim_config = (known after apply)
- self_hosted_domains = [
- "example.com",
] -> null
+ skip_app_launcher_login_page = false
- tags = [] -> null
+ target_criteria = (known after apply)
~ updated_at = "2025-04-18T09:52:57Z" -> (known after apply)
# (11 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_group.group["Admins ips"] will be updated in-place
~ resource "cloudflare_zero_trust_access_group" "group" {
~ created_at = "2025-03-25T13:30:58Z" -> (known after apply)
id = "8723aad0-8b14-4f39-c293233fbb6d"
~ include = [
~ {
~ ip = {
~ ip = "2a02:2f0f:c00::/64" -> "2a02:2f0f:c00:d159:548e:6bbd/64"
}
},
# (5 unchanged elements hidden)
]
name = "Admins ips"
~ require = [] -> (known after apply)
~ updated_at = "2025-04-18T09:52:55Z" -> (known after apply)
# (2 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_identity_provider.provider["OpenID Connect"] will be updated in-place
~ resource "cloudflare_zero_trust_access_identity_provider" "provider" {
~ config = {
+ client_secret = (sensitive value)
~ redirect_url = "https://example.cloudflareaccess.com/cdn-cgi/access/callback" -> (known after apply)
# (5 unchanged attributes hidden)
}
id = "f26b2aeb-2b29-41de-cf3be7392ead"
name = "Name SSO"
~ scim_config = {
+ scim_base_url = (known after apply)
- seat_deprovision = false -> null
+ secret = (sensitive value)
- user_deprovision = false -> null
# (1 unchanged attribute hidden)
}
# (2 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Everyone"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 0 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "94a93801-209c-4c36-e8a6cac51d89"
+ isolation_required = false
name = "Everyone"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:52:56Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by email"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 1 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "6bebb1b4-0da3-a77e-e617d31bde08"
+ isolation_required = false
name = "Filter by email"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:52:56Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by email nifi"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 1 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "47efe264-4c3f-a883-2663da932e70"
+ isolation_required = false
name = "Filter by email nifi"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:52:56Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
# cloudflare_zero_trust_access_policy.policy["Filter by ip"] will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "policy" {
~ app_count = 2 -> (known after apply)
+ approval_groups = (known after apply)
+ approval_required = false
~ created_at = "2025-03-25T13:31:04Z" -> (known after apply)
id = "ceda7e11-5421-4d49-1e9da73fa590"
+ isolation_required = false
name = "Filter by ip"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-04-18T09:52:56Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
Plan: 0 to add, 8 to change, 0 to destroy.
Clearly this is a consequence of doing the fully automatic generation. The api will return a full object on a GET, even if the terraform object has not set the properties. This is especially obvious when setting policies on an application:
(Notice how the ID have not changed but simply the properties on the policy object that is managed somewhere else.
All properties on the policies objects are retrieved on GET from the API, and since technically it is possible to set these properties on the terraform object (because it is autogenerated) it would be wholly redundant to set the name of a policy that I am referencing by ID.
HOWEVER, even with full on ignore_changes on every change the provider suggests for an access application, it will still want to make an apply with all of it simply updates from the API:
(and yes I have added ignore changes for footer_links, and path_cookie_attribute etc, but either it complains that it is a redundant ignore or it simply ignores the ignore.
And for anyone who cares about minimizing the output (but not removing the constant apply) this is my ignore in Terraform:
lifecycle {
ignore_changes = [
destinations, self_hosted_domains, path_cookie_attribute, skip_app_launcher_login_page,
policies.0.name, policies.0.decision, policies.0.exclude, policies.0.include, policies.0.connection_rules, policies.0.require,
policies.1.name, policies.1.decision, policies.1.exclude, policies.1.include, policies.1.connection_rules, policies.1.require
]
}
It gives a warning The attribute "self_hosted_domains" is deprecated. but without it, it wants to change the property
Sidenote:
Adding this, will STILL make the resource wanting to update
lifecycle {
ignore_changes = all
}
FWIW, cloudflare_zero_trust_organization seems to be affected as well.
has there been any word from cloudflare team on a fix for this? obviously it's not mission critical but man is this bug annoying
Discussed during the triage today, and wanted to confirm that this one is not fixed in the upcoming 5.4.0, but we're still looking.
This resource has been giving me hell. it's simply impossible to use.
+1 this is an issue for us too
Unfortunately, we are also running into this issue regarding the cloudflare_zero_trust_access_application resource. It seems like this was open about a month ago and is impacting our now updated terraform repo and confusing users. Has anyone got a workaround or is there a possible fix for this?
@ronballesteros Not to my knowledge. I've just been holding off on upgrading my modules to 5.x because of all the bugs with Zero Trust resources. 🙁
@ronballesteros version 5.1.0 works for us
@ronballesteros version 5.1.0 works for us
its strange, can you confirm? Try another resources like cloudflare_access_rule or anything else in cloudflare provider
On the latest version 5.5 we are now seeing an error that completely fails the apply :
Error: Provider produced inconsistent result after apply
│
│ When applying changes to
│ cloudflare_zero_trust_access_policy.cloudflare_bypass, provider
│ "provider[\"registry.terraform.io/cloudflare/cloudflare\"]" produced an
│ unexpected new value: .app_count: was cty.NumberIntVal(0), but now
│ cty.NumberIntVal(2).
│
│ This is a bug in the provider, which should be reported in the provider's
│ own issue tracker.
Edit, can see this is reported in #5608
yea we had the same, had to pin to v5.4.
I understand why CF team wants to go with the auto generated approach for the provider, but so far the result has been a disaster.
Wish I had shipped our new codebase on the v4 provider.
yea we had the same, had to pin to v5.4.
I understand why CF team wants to go with the auto generated approach for the provider, but so far the result has been a disaster.
Wish I had shipped our new codebase on the v4 provider.
We implemented a workaround for the issue in 5.5 which works:
lifecycle {
ignore_changes = [app_count, reusable]
}
I'm having the same issues where the fields pulled from the cloudflare_zero_trust_access_policy resources referenced in the policies list apparently ignored/reset when Terraform proposes the plan. This is with v5.5.0. I don't want to have to set temporary lifecycle ignore policies on a bunch of resources throughout the code to avoid clobbering our infrastructure.
After adding ignore to all
lifecycle {
ignore_changes = all
}
the diff is shown as below:
~ resource "cloudflare_zero_trust_access_application" "test" {
~ aud = "dc7b25bfc7d0aa7dbc06406a910a3dc3b17b270025a66d9fa37c9115d9c040af" -> (known after apply)
~ created_at = "2025-06-02T12:43:46Z" -> (known after apply)
id = "355886c2-d2bf-4514-93b6-5748227d3111"
+ landing_page_design = (known after apply)
name = "test"
+ path_cookie_attribute = false
+ saas_app = (known after apply)
+ skip_app_launcher_login_page = false
tags = []
~ updated_at = "2025-06-02T13:37:18Z" -> (known after apply)
# (13 unchanged attributes hidden)
}
It seems like the issue is that the provider doesn't see the current state for some of the fields above, values from the state file.
"aud": "dc7b25bfc7d0aa7dbc06406a910a3dc3b17b270025a66d9fa37c9115d9c040af", (matches)
"created_at": "0001-01-01T00:00:00Z",
"landing_page_design": null,
"path_cookie_attribute": false,
"saas_app": null,
"skip_app_launcher_login_page": false,
I'd bet that issue is with bugged created_at or one of the attributes that already match value but still show as diff path_cookie_attribute or skip_app_launcher_login_page
provider v5.5.0
Is there a known work-around?
@per-lind @octavian2204 - can confirm that I don't see the changes for cloudflare_zero_trust_access_application on version 5.1.0, however, we got other application changes for other resources such as cloudflare_zero_trust_access_policy.
Terraform will perform the following actions:
# cloudflare_zero_trust_access_policy.<redacted> will be updated in-place
~ resource "cloudflare_zero_trust_access_policy" "<redacted>" {
~ app_count = 8 -> (known after apply)
~ approval_groups = [] -> (known after apply)
+ approval_required = false
~ created_at = "2024-06-19T16:56:14Z" -> (known after apply)
id = "<redacted>"
+ isolation_required = false
name = "<redacted>"
+ purpose_justification_required = false
~ reusable = true -> (known after apply)
~ updated_at = "2025-05-21T20:45:39Z" -> (known after apply)
# (6 unchanged attributes hidden)
}
Plan: 0 to add, 1 to change, 0 to destroy.
I downgraded to 5.1.0 but still have loads of changes for cloudflare_zero_trust_access_application.
I ended up with following workaround:
variable "cf_zero_trust_workaround" {
type = bool
default = true
}
resource "cloudflare_zero_trust_access_application" "apps" {
for_each = var.name == "live" ? {} : (var.cf_zero_trust_workaround == true ? {} : local.domains_apex_only)
}
It hides all cloudflare_zero_trust_access_application after creation via cf_zero_trust_workaround flag.
Here is a script in Nushell to delete them from the state:
tf plan -- -out .tmp/plan.out
tf show -- -json .tmp/plan.out | from json | get
(tf show -- -json .tmp/plan.out | from json
| get resource_changes
| select address change
| where { ($in | get change | get actions | first) == "delete" }
| get address
| each { terraform state rm $in })
Has anyone tested on this with version 5.6.0?
Has anyone tested on this with version
5.6.0?
@cpapad I recently reran our migration workflow with 5.6.0 and it's still doing the same thing.
Has anyone tested on this with version
5.6.0?@cpapad I recently reran our migration workflow with
5.6.0and it's still doing the same thing.
Thank you! I'll stick with 5.1.0 until this is resolved
I'm seeing the same issues as others. Has a root cause been found at least?
I have the bug with these attributes in 5.6.0: landing_page_design, path_cookie_attribute, saas_app, skip_app_launcher_login_page. And of course I defined everything, but still I have to ignore policies if I don't want 20 more lines of change for each app. Anyone knows how can we put someone from cloudflare on it ?