-
-
Notifications
You must be signed in to change notification settings - Fork 210
Description
Issue submitter TODO list
- I've looked up my issue in FAQ
- I've searched for an already existing issues here
- I've tried running
main-labeled docker image and the issue still persists there - I'm running a supported version of the application which is listed here
Describe the bug (actual behavior)
After upgrading to Kafbat 1.2.0 via Helm Chart 1.4.12, it is expected that we have support for using regex to identify subjects for roles when configuring RBAC permissions. We use Microsoft Entra ID as a generic OAuth2 Provider, with custom-params configured to set the roles-field to roles, which allows us to utilise App Roles within EntraID to assign our users to the subjects Kafbat is configured to read.
Our redacted OAuth configuration is this:
type: OAUTH2
oauth2:
client:
azure:
clientId: <redacted>
clientSecret: <redacted>
scope: openid
client-name: azure
provider: azure
issuer-uri: <redacted>
jwk-set-uri: <redacted>
user-name-attribute: email
custom-params:
type: oauth
roles-field: roles Our RBAC is configured like this:
rbac:
roles:
- name: "readonly-global"
clusters:
- dev
subjects:
- provider: oauth
type: role
value: ".*-ADMIN"
isRegex: true
permissions:
- resource: clusterconfig
actions: [ "view" ]
- resource: topic
value: ".*"
actions:
- VIEW
- resource: consumer
value: ".*"
actions: [ view ]
- resource: schema
value: ".*"
actions: [ view ]
- resource: connect
value: ".*"
actions: [ view ]
- resource: acl
actions: [ view ]
- name: "readdelete-testrole"
clusters:
- dev
subjects:
- provider: oauth
type: role
value: "dev.engsoft.user"
permissions:
- resource: topic
value: mgp.engsoft\..*
actions:
- MESSAGES_READ
- MESSAGES_DELETEWithin Azure, I have two roles assigned: dev.engsoft.user via a group assignment and KAFBAT-ADMIN via direct assignment. Both groups are present in the token sent to Kafbat, which can be seen in the logs, however, Kafbat does not respect the regex assignment of .*-ADMIN and only assigns roles that exactly match, regardless of the isRegex field value.
Here are logs of this with the above configuration:
2025-03-25 16:30:04,457 TRACE [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: Extracting OAuth2 user authorities
2025-03-25 16:30:04,458 DEBUG [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: Principal name is: [<redacted email>]
2025-03-25 16:30:04,459 DEBUG [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: Matched roles by username: []
2025-03-25 16:30:04,459 TRACE [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: The field is either a set or a list, returning as is
2025-03-25 16:30:04,459 DEBUG [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: Token's groups: [KAFBAT-ADMIN,dev.engsoft.user]
2025-03-25 16:30:04,459 DEBUG [reactor-http-epoll-9] i.k.u.s.r.e.OauthAuthorityExtractor: Matched group roles: [readdelete-testrole]
Setting the subject to the following shows the permission successfully assigns:
subjects:
- provider: oauth
type: role
value: "KAFBAT-ADMIN"
isRegex: true2025-03-25 16:56:18,855 TRACE [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: Extracting OAuth2 user authorities
2025-03-25 16:56:18,855 DEBUG [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: Principal name is: [<redacted email>]
2025-03-25 16:56:18,856 DEBUG [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: Matched roles by username: []
2025-03-25 16:56:18,856 TRACE [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: The field is either a set or a list, returning as is
2025-03-25 16:56:18,856 DEBUG [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: Token's groups: [KAFBAT-ADMIN,dev.engsoft.user]
2025-03-25 16:56:18,857 DEBUG [reactor-http-epoll-8] i.k.u.s.r.e.OauthAuthorityExtractor: Matched group roles: [readonly-global, readdelete-testrole]
It appears that the configuration of isRegex is ignored entirely. For the record, the regex we use for topic naming permissions within these roles all work as expected, which points directly to the implementation of Subject regex parsing.
Expected behavior
It is expected that for a regex, Kafbat matches any roles that succeed against that regex to the group. The above .*-ADMIN example is taken directly from the documentation - in reality, we want it to match an even simpler regex of .* so we can assign any role a set of global default permissions.
Your installation details
We're running:
- App version v1.2.0 3074abc
- Helm chart version 1.4.12
yamlApplicationConfig:
kafka:
internalTopicPrefix: _ui_
clusters:
- name: dev
bootstrapServers: dev-kafka-bootstrap.dev-kafka.svc.cluster.local:9092
schemaRegistry: http://conf-schema-registry:8081
readonly: false
properties:
security:
protocol: SASL_PLAINTEXT
sasl:
mechanism: PLAIN
jaas:
config: org.apache.kafka.common.security.plain.PlainLoginModule required username="<redacted>" password="<redacted>" ;
auth:
type: OAUTH2
oauth2:
client:
azure:
clientId: <redacted>
clientSecret: <redacted>
scope: openid
client-name: azure
provider: azure
issuer-uri: <redacted>
jwk-set-uri: <redacted>
user-name-attribute: email
custom-params:
type: oauth
roles-field: roles
logging:
level:
root: info # trace,debug, info, warn, error. default: info
io.kafbat.ui.service.rbac: TRACE
rbac:
roles:
- name: "readonly-global"
clusters:
- dev
subjects:
- provider: oauth
type: role
value: "KAFBAT-ADMIN"
isRegex: true
permissions:
- resource: clusterconfig
actions: [ "view" ]
- resource: topic
value: ".*"
actions:
- VIEW
- resource: consumer
value: ".*"
actions: [ view ]
- resource: schema
value: ".*"
actions: [ view ]
- resource: connect
value: ".*"
actions: [ view ]
- resource: acl
actions: [ view ]
- name: "readdelete-testrole"
clusters:
- dev
subjects:
- provider: oauth
type: role
value: "dev.engsoft.user"
permissions:
- resource: topic
value: mgp.engsoft\..*
actions:
- MESSAGES_READ
- MESSAGES_DELETESteps to reproduce
Deploy Kafbat via chart with the above configuration and correct setup in EntraID and the result is reproducible.
Screenshots
No response
Logs
Additional context
This was discussed in the community Discord. We tried the suggestion of changing isRegex to isIsRegex but this didn't work.
