Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

google_compute_firewall does not accept null for ports on icmp #17946

Open
dw185190 opened this issue Apr 24, 2024 · 2 comments
Open

google_compute_firewall does not accept null for ports on icmp #17946

dw185190 opened this issue Apr 24, 2024 · 2 comments

Comments

@dw185190
Copy link

dw185190 commented Apr 24, 2024

Community Note

  • Please vote on this issue by adding a 👍 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.
  • If an issue is assigned to a user, that user is claiming responsibility for the issue.
  • Customers working with a Google Technical Account Manager or Customer Engineer can ask them to reach out internally to expedite investigation and resolution of this issue.

Terraform Version

Terraform v1.8.1
on linux_amd64

  • provider registry.terraform.io/hashicorp/google v4.82.0
  • provider registry.terraform.io/hashicorp/local v2.5.1

Affected Resource(s)

google_compute_firewall

Terraform Configuration

snippet.tfvars
target_pp = ["tcp:22,6443","udp:123,456", "icmp:"]

snippet.tf

locals {
  pp = {
    for obj in var.target_pp : obj => {
      protocol = split(":", obj )[0]
      ports = split(",", split(":", obj )[1])
    }
  }
}

resource "google_compute_firewall" "rule-vpc-peering-ingress" {
  for_each = local.pp
  description = "Allow the Argo instances access to DSDS instances"
  name        = "allow-${each.value.protocol}${join("",each.value.ports)}-ingress"
  network     = var.source_vpc_name
  direction   = "INGRESS"
  priority    = "100"
  source_ranges = [var.target_cidr]
  target_tags = [var.target_tag]

  allow {
    protocol = each.value.protocol
    ports    = each.value.ports
  }
}

Debug Output

│ Error: Error creating Firewall: googleapi: Error 400: Invalid value for field 'resource.allowed[0].ports[0]': ''. Ports may only be specified on rules whose protocol is one of [TCP, UDP, SCTP]., invalid

│ with module.vpc-peering["subnet1"].google_compute_firewall.rule-vpc-peering-ingress["icmp:"],
│ on modules/vpc-peering/main.tf line 32, in resource "google_compute_firewall" "rule-vpc-peering-ingress":
│ 32: resource "google_compute_firewall" "rule-vpc-peering-ingress" {

Expected Behavior

Although ICMP does not have ports, to be able to reuse the google_compute_firewall resource for ICMP and other protocols is useful for compact and effective IaC.

ie. populated ports with a value for non ICMP and null for ICMP

eg. target_pp = ["tcp:22,6443","udp:123,456", "icmp:"]

This Provider should allow:
a) No ports defined in the Terraform <-- it currently does this
And
b) Ports to be defined but with a null value <-- currently it fails as debug output above.

Actual Behavior

Note, that the Terraform plan shows the null value as expected
eg.

      + allow {
          + ports    = [
              + null,
            ]
          + protocol = "icmp"
        }

it is the apply that fails
eg.
Error: Error creating Firewall: googleapi: Error 400: Invalid value for field 'resource.allowed[0].ports[0]': ''. Ports may only be specified on rules whose protocol is one of [TCP, UDP, SCTP]., invalid

Steps to reproduce

  1. terraform apply

Important Factoids

No response

References

No response

b/337926849

@dw185190
Copy link
Author

FYI
My current workaround is something like this, but this makes me curl up in a ball and cry like a baby ;)

  dynamic "allow" {
    for_each = (each.value.protocol != "icmp" ? toset([each.value.protocol]) : toset([]))
    content {
      protocol = each.value.protocol
      ports    = each.value.ports
    }
  }

  dynamic "allow" {
    for_each = (each.value.protocol == "icmp" ? toset([each.value.protocol]) : toset([]))
    content {
      protocol = each.value.protocol
    }
  }

@ggtisc
Copy link
Collaborator

ggtisc commented Apr 29, 2024

Confirmed issue, after many tries with different configurations it is not possible to manage ICMP for firewall rules even if the value is assigned or not, when the documentation specify that this is valid

@ggtisc ggtisc self-assigned this Apr 29, 2024
@ggtisc ggtisc removed the forward/review In review; remove label to forward label Apr 29, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants