Redpanda ACLs are a bit of a shell game, making you think you’re controlling access to topics, but you’re actually controlling access to principals that might have access to topics.
Let’s see it in action. Imagine a Redpanda cluster running on localhost:9092. We want to create a user, alice, and give her read-only access to a topic named my-topic.
First, we need to add alice to Redpanda. This isn’t an ACL itself, but it’s a prerequisite. We use the rpk tool for this:
rpk user add alice --password "supersecret"
Now, let’s grant alice the permission to read my-topic. The rpk command looks like this:
rpk acl grant --principal User:alice --operation READ --resource topic:my-topic
What just happened? We didn’t tell Redpanda "Alice can read my-topic." Instead, we told it: "For any principal named User:alice, if they also happen to be associated with the READ operation and the topic:my-topic resource, then allow it." This indirectness is key. Redpanda doesn’t store a list of users per topic; it stores a list of rules that match principals to operations on resources.
This means we can grant permissions to roles, and then assign users to those roles. Let’s create a developer role:
rpk acl grant --principal Role:developer --operation READ --resource topic:my-topic
rpk acl grant --principal Role:developer --operation WRITE --resource topic:my-topic
Now, any user assigned to the developer role will automatically get read and write access to my-topic. To assign alice to this role, we use the rpk user alter command:
rpk user alter alice --add-role developer
The system’s internal model works by evaluating these ACL entries. When a client (like a Kafka producer or consumer) tries to perform an operation, Redpanda checks its ACLs. It looks for any entry that matches the client’s principal (e.g., User:alice), the requested operation (e.g., READ), and the target resource (e.g., topic:my-topic). If it finds an entry with ALLOW, the operation proceeds. If it finds an entry with DENY, the operation is blocked. If no matching entry is found, the default behavior is typically to deny the operation.
The surprising thing is how Redpanda resolves principal identities. While we often think of User:alice, Redpanda can also authenticate using SASL mechanisms that map to different principal types, such as Kerberos principals (User:alice@REALM). The ACL system doesn’t inherently distinguish between a locally managed user and a user authenticated via an external system, as long as the principal name format is consistent. This allows for flexible integration with existing identity management infrastructure.
The resource part of an ACL entry is also more powerful than just topics. You can specify group:<group-id> for consumer group management, cluster for cluster-level operations, or even transactional-id:<id> for transactional capabilities.
Understanding this principal-centric, rule-based evaluation is crucial. It means you can revoke access not by removing a user from a topic, but by removing their association with a role that grants access, or by revoking the role’s permission on the topic itself.
The next step in managing access is understanding how to use wildcard characters in your ACLs to manage broader sets of resources or principals.