Back to Checks
aws

Kafka cluster is not publicly accessible

kafka_cluster_is_public
Service: kafkaSeverity: critical
OfficialBuilt-inVerified
Categories:internet-exposed
Resource Type:AwsMskCluster

Amazon MSK clusters with broker endpoints exposed to the public Internet.

Serverless clusters are private by default; provisioned clusters are evaluated for their public access configuration.

Risk

Public brokers erode CIA:

  • Confidentiality: unauthorized consumers can read topics
  • Integrity: rogue producers inject or alter events
  • Availability: floods or scans strain brokers

This enables metadata enumeration, data exfiltration, stream poisoning, and costly egress.

Run this check with Prowler

Run in Prowler Cloud
Run
prowler aws --checks kafka_cluster_is_public

Recommendation

Keep brokers private within the VPC by disabling public access and limiting exposure to trusted networks.

Enforce strong auth (SASL/IAM, SASL/SCRAM, or mTLS), require TLS, and apply Kafka ACLs. Provide access via VPN, bastion, or private networking (peering/Transit Gateway). Apply least privilege and monitor broker connections.

Remediation

CLI

aws kafka update-connectivity --cluster-arn <CLUSTER_ARN> --current-version <CURRENT_CLUSTER_VERSION> --connectivity-info '{"PublicAccess":{"Type":"DISABLED"}}'

Terraform

# Terraform: ensure MSK cluster is not publicly accessible
resource "aws_msk_cluster" "<example_resource_name>" {
  cluster_name           = "<example_resource_name>"
  kafka_version          = "2.8.1"
  number_of_broker_nodes = 2

  broker_node_group_info {
    client_subnets = [
      "<example_subnet_id_1>",
      "<example_subnet_id_2>",
    ]
    instance_type = "kafka.t3.small"

    connectivity_info {
      public_access {
        type = "DISABLED"  # Critical: disables public access to brokers
      }
    }
  }
}

NativeIaC

# CloudFormation: ensure MSK cluster is not publicly accessible
Resources:
  <example_resource_name>:
    Type: AWS::MSK::Cluster
    Properties:
      ClusterName: <example_resource_name>
      KafkaVersion: "2.8.1"
      NumberOfBrokerNodes: 2
      BrokerNodeGroupInfo:
        ClientSubnets:
          - <example_subnet_id_1>
          - <example_subnet_id_2>
        InstanceType: kafka.t3.small
        ConnectivityInfo:
          PublicAccess:
            Type: DISABLED  # Critical: disables public access to brokers

Other

1Open the Amazon MSK console
2Select your cluster and go to the Properties tab
3In Network settings, click Edit public access
4Set Public access to Disabled (Off)
5Click Save changes

Check Code

from prowler.lib.check.models import Check, Check_Report_AWS
from prowler.providers.aws.services.kafka.kafka_client import kafka_client


class kafka_cluster_is_public(Check):
    def execute(self):
        findings = []

        for cluster in kafka_client.clusters.values():
            report = Check_Report_AWS(metadata=self.metadata(), resource=cluster)
            report.status = "FAIL"
            report.status_extended = (
                f"Kafka cluster {cluster.name} is publicly accessible."
            )

            # Serverless clusters are always private by default
            if cluster.kafka_version == "SERVERLESS":
                report.status = "PASS"
                report.status_extended = f"Kafka cluster {cluster.name} is serverless and always private by default."
            # For provisioned clusters, check the public access configuration
            elif not cluster.public_access:
                report.status = "PASS"
                report.status_extended = (
                    f"Kafka cluster {cluster.name} is not publicly accessible."
                )

            findings.append(report)

        return findings