id: gcloud-vm-public-ip-enabled

info:
  name: VM Instance Using Public IP Address
  author: princechaddha
  severity: high
  description: |
    Ensure that your Google Compute Engine instances are not configured to have external IP addresses in order to minimize their exposure to the Internet. To reduce attack surface, Google Cloud virtual machine (VM) instances should not have public IP addresses attached. Instead, VM instances should be configured to run behind load balancers.
  impact: |
    VM instances with public IP addresses are directly exposed to the internet, increasing the attack surface and risk of unauthorized access.
  remediation: |
    Remove external IP addresses from your VM instances using the 'gcloud compute instances delete-access-config' command or through the Google Cloud Console. Configure instances to run behind load balancers instead.
  reference:
    - https://www.trendmicro.com/cloudoneconformity/knowledge-base/gcp/ComputeEngine/instances-with-public-ip-addresses.html
    - https://cloud.google.com/compute/docs/ip-addresses/reserve-static-external-ip-address
  tags: cloud,devops,gcp,gcloud,compute,security,networking,public-ip,gcp-cloud-config

flow: |
  code(1)
  for(let projectId of iterate(template.projectIds)){
    set("projectId", projectId)
    code(2)
    for(let instance of iterate(template.instances)){
      instance = JSON.parse(instance)
      set("instanceName", instance.name)
      set("zone", instance.zone)
      code(3)
    }
  }

self-contained: true

code:
  - engine:
      - sh
      - bash
    source: |
      gcloud projects list --format="json(projectId)"

    extractors:
      - type: json
        name: projectIds
        internal: true
        json:
          - '.[].projectId'

  - engine:
      - sh
      - bash
    source: |
      gcloud compute instances list --project $projectId --format="json(name,zone.basename())"

    extractors:
      - type: json
        name: instances
        internal: true
        json:
          - '.[]'

  - engine:
      - sh
      - bash
    source: |
      gcloud compute instances describe $instanceName --zone $zone --project $projectId --format="json(networkInterfaces[].accessConfigs)"

    matchers-condition: and
    matchers:
      - type: word
        words:
          - '"natIP":'
        negative: true

      - type: word
        words:
          - '"accessConfigs":'

    extractors:
      - type: dsl
        dsl:
          - '"VM instance " + instanceName + " in zone " + zone + " of project " + projectId + " has a public IP address configured"'
# digest: 4a0a00473045022027df1ce5767c979d874c287167abb6653905fb39d078890c8aebb9341c8cf470022100f7793e24948701647d8a263c6e45dfe4d47ed9431777632f3c8dbd49948f171e:922c64590222798bb761d5b6d8e72950