Skip to content

Commit 46698e3

Browse files
committed
feat(KONFLUX-9093): Add tool for validating role RBAC
In KONFLUX-9093, there is a request to enable roles to be cerated in namespaces via Argo. In order to allow this, we need to be able to guarantee that the roles are not granting permissions that users would normally not have (but which Argo would have). We can use k8s tooling to ensure that permissions are not exceeding some reference roles. Co-Authored-By: Claude <[email protected]> Signed-off-by: arewm <[email protected]> rh-pre-commit.version: 2.3.2 rh-pre-commit.check-secrets: ENABLED
1 parent 2083a26 commit 46698e3

25 files changed

+2033
-7
lines changed

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
tools/rbac-validator
2+
*/venv

.tekton/ci-checks.yaml

Lines changed: 140 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,140 @@
1+
apiVersion: tekton.dev/v1
2+
kind: Task
3+
metadata:
4+
name: ci-checks
5+
labels:
6+
app.kubernetes.io/version: "0.1"
7+
annotations:
8+
tekton.dev/pipelines.minVersion: "0.12.1"
9+
tekton.dev/categories: CI
10+
tekton.dev/tags: ci,golang,rbac,validation
11+
tekton.dev/displayName: "CI Checks"
12+
tekton.dev/platforms: "linux/amd64,linux/arm64"
13+
spec:
14+
description: >-
15+
This task runs CI checks for the RBAC validator tool including format checking,
16+
linting, testing, and build verification. It uses the trusted artifact pattern
17+
to retrieve source code.
18+
params:
19+
- name: SOURCE_ARTIFACT
20+
description: The Trusted Artifact URI pointing to the application source code
21+
type: string
22+
- name: WORKING_DIR
23+
description: Working directory for the CI checks
24+
type: string
25+
default: "tools"
26+
- name: GO_VERSION
27+
description: Go version to use for building and testing
28+
type: string
29+
default: "1.22"
30+
results:
31+
- name: TEST_OUTPUT
32+
description: Output from the test execution
33+
- name: BUILD_STATUS
34+
description: Status of the build process
35+
volumes:
36+
- name: workdir
37+
emptyDir: {}
38+
stepTemplate:
39+
volumeMounts:
40+
- mountPath: /var/workdir
41+
name: workdir
42+
steps:
43+
- name: use-trusted-artifact
44+
image: quay.io/redhat-appstudio/build-trusted-artifacts:latest@sha256:4e39fb97f4444c2946944482df47b39c5bbc195c54c6560b0647635f553ab23d
45+
args:
46+
- use
47+
- $(params.SOURCE_ARTIFACT)=/var/workdir/source
48+
volumeMounts:
49+
- mountPath: /var/workdir
50+
name: workdir
51+
52+
- name: ci-checks
53+
image: registry.access.redhat.com/ubi9/go-toolset:1.24.4-1754467841@sha256:3f552f246b4bd5bdfb4da0812085d381d00d3625769baecaed58c2667d344e5c
54+
workingDir: /var/workdir/source/$(params.WORKING_DIR)
55+
env:
56+
- name: GOCACHE
57+
value: /var/workdir/.cache/go-build
58+
- name: GOMODCACHE
59+
value: /var/workdir/.cache/go-mod
60+
- name: CGO_ENABLED
61+
value: "0"
62+
script: |
63+
#!/bin/bash
64+
set -uo pipefail
65+
66+
# Track overall success
67+
OVERALL_SUCCESS=true
68+
69+
echo "=== Starting CI checks for RBAC validator ==="
70+
# Ensure we're in the tools directory
71+
if [[ ! -f "rbac-validator.go" ]]; then
72+
echo "Error: rbac-validator.go not found in current directory"
73+
echo "Current directory contents:"
74+
ls -la
75+
exit 1
76+
fi
77+
78+
# Create cache directories
79+
mkdir -p /var/workdir/.cache/go-build /var/workdir/.cache/go-mod
80+
81+
echo "=== Installing golangci-lint ==="
82+
export PATH=$PATH:$(go env GOPATH)/bin
83+
go install github.com/golangci/golangci-lint/cmd/[email protected]
84+
85+
echo "=== Running format check ==="
86+
if [ -n "$(gofmt -l .)" ]; then
87+
echo "Code is not formatted. Files needing formatting:"
88+
gofmt -l .
89+
echo "FAIL: Code formatting check failed"
90+
exit 1
91+
fi
92+
echo "PASS: Code formatting check"
93+
94+
echo "=== Running golangci-lint ==="
95+
export PATH=$PATH:$(go env GOPATH)/bin
96+
if golangci-lint run --build-tags="" --max-issues-per-linter=0 --max-same-issues=0; then
97+
echo "PASS: Linting check"
98+
else
99+
echo "FAIL: Linting check"
100+
OVERALL_SUCCESS=false
101+
fi
102+
103+
echo "=== Building binary ==="
104+
if go build -o rbac-validator rbac-validator.go; then
105+
echo "PASS: Binary build"
106+
else
107+
echo "FAIL: Binary build"
108+
OVERALL_SUCCESS=false
109+
fi
110+
111+
echo "=== Running tests ==="
112+
if go test -v ./... | tee /var/workdir/test-output.txt; then
113+
echo "PASS: All tests"
114+
else
115+
echo "FAIL: All tests"
116+
OVERALL_SUCCESS=false
117+
fi
118+
119+
echo "=== Running testdata validation tests ==="
120+
if go test -v -run "TestAllowedRoles|TestDeniedRoles|TestBinaryWithTestData|TestTestDataCompleteness"; then
121+
echo "PASS: Testdata validation"
122+
else
123+
echo "FAIL: Testdata validation"
124+
OVERALL_SUCCESS=false
125+
fi
126+
127+
128+
if [ "$OVERALL_SUCCESS" = "true" ]; then
129+
echo "=== All CI checks completed successfully ==="
130+
else
131+
echo "=== CI checks completed with failures ==="
132+
exit 1
133+
fi
134+
volumeMounts:
135+
- mountPath: /var/workdir
136+
name: workdir
137+
# git clone is made as user 0, so we need to be this user too because
138+
# the trusted artifacts are restored as this user as well.
139+
securityContext:
140+
runAsUser: 0

.tekton/konflux-release-data-ci-worker-pull-request.yaml

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,15 @@ metadata:
1010
pipelinesascode.tekton.dev/max-keep-runs: "3"
1111
pipelinesascode.tekton.dev/on-cel-expression: event == "pull_request" && target_branch == "main" &&
1212
( ".tekton/konflux-release-data-ci-worker-pull-request.yaml".pathChanged() ||
13+
".tekton/ci-checks.yaml".pathChanged() ||
1314
"Containerfile".pathChanged() ||
1415
"rpms.lock.yaml".pathChanged() ||
15-
"requirements.txt".pathChanged() )
16+
"requirements.txt".pathChanged() ||
17+
"tools/rbac-validator.go".pathChanged() ||
18+
"tools/rbac-validator_test.go".pathChanged() ||
19+
"tools/Makefile".pathChanged() ||
20+
"tools/.golangci.yml".pathChanged() ||
21+
"tools/testdata/**".pathChanged() )
1622
creationTimestamp: null
1723
labels:
1824
appstudio.openshift.io/application: konflux-release-data-ci
@@ -38,7 +44,7 @@ spec:
3844
- name: path-context
3945
value: .
4046
- name: prefetch-input
41-
value: '{"packages": [{"type": "pip", "path": "."}, {"type": "rpm", "path": "."}]}'
47+
value: '{"packages": [{"type": "pip", "path": "."}, {"type": "rpm", "path": "."}, {"type": "gomod", "path": "tools"}]}'
4248
pipelineSpec:
4349
description: |
4450
This pipeline is ideal for building multi-arch container images from a Containerfile while maintaining trust after pipeline customization.
@@ -214,6 +220,22 @@ spec:
214220
workspace: git-auth
215221
- name: netrc
216222
workspace: netrc
223+
- name: ci-checks
224+
params:
225+
- name: SOURCE_ARTIFACT
226+
value: $(tasks.prefetch-dependencies.results.SOURCE_ARTIFACT)
227+
- name: WORKING_DIR
228+
value: "tools"
229+
runAfter:
230+
- prefetch-dependencies
231+
taskRef:
232+
kind: Task
233+
name: ci-checks
234+
when:
235+
- input: $(tasks.init.results.build)
236+
operator: in
237+
values:
238+
- "true"
217239
- matrix:
218240
params:
219241
- name: PLATFORM

.tekton/konflux-release-data-ci-worker-push.yaml

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,15 @@ metadata:
99
pipelinesascode.tekton.dev/max-keep-runs: "3"
1010
pipelinesascode.tekton.dev/on-cel-expression: event == "push" && target_branch == "main" &&
1111
( ".tekton/konflux-release-data-ci-worker-push.yaml".pathChanged() ||
12+
".tekton/ci-checks.yaml".pathChanged() ||
1213
"Containerfile".pathChanged() ||
1314
"rpms.lock.yaml".pathChanged() ||
14-
"requirements.txt".pathChanged() )
15+
"requirements.txt".pathChanged() ||
16+
"tools/rbac-validator.go".pathChanged() ||
17+
"tools/rbac-validator_test.go".pathChanged() ||
18+
"tools/Makefile".pathChanged() ||
19+
"tools/.golangci.yml".pathChanged() ||
20+
"tools/testdata/**".pathChanged() )
1521
creationTimestamp: null
1622
labels:
1723
appstudio.openshift.io/application: konflux-release-data-ci
@@ -35,7 +41,7 @@ spec:
3541
- name: path-context
3642
value: .
3743
- name: prefetch-input
38-
value: '{"packages": [{"type": "pip", "path": "."}, {"type": "rpm", "path": "."}]}'
44+
value: '{"packages": [{"type": "pip", "path": "."}, {"type": "rpm", "path": "."}, {"type": "gomod", "path": "tools"}]}'
3945
pipelineSpec:
4046
description: |
4147
This pipeline is ideal for building multi-arch container images from a Containerfile while maintaining trust after pipeline customization.
@@ -211,6 +217,22 @@ spec:
211217
workspace: git-auth
212218
- name: netrc
213219
workspace: netrc
220+
- name: ci-checks
221+
params:
222+
- name: SOURCE_ARTIFACT
223+
value: $(tasks.prefetch-dependencies.results.SOURCE_ARTIFACT)
224+
- name: WORKING_DIR
225+
value: "tools"
226+
runAfter:
227+
- prefetch-dependencies
228+
taskRef:
229+
kind: Task
230+
name: ci-checks
231+
when:
232+
- input: $(tasks.init.results.build)
233+
operator: in
234+
values:
235+
- "true"
214236
- matrix:
215237
params:
216238
- name: PLATFORM

Containerfile

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,24 @@
11
FROM quay.io/konflux-ci/yq@sha256:15d0238843d954ee78c9c190705eb8b36f6e52c31434183c37d99a80841a635a as yq
22
FROM registry.redhat.io/openshift4/ose-cli-artifacts-rhel9:v4.17.0-202504091537.p0.g0000b3e.assembly.stream.el9 as oc
33

4+
# Build stage for RBAC validator
5+
FROM registry.access.redhat.com/ubi9/go-toolset:1.24.4-1754467841@sha256:3f552f246b4bd5bdfb4da0812085d381d00d3625769baecaed58c2667d344e5c as go-builder
6+
7+
# Copy tools directory and build the binary
8+
COPY --chown=default tools/ /workspace/tools/
9+
WORKDIR /workspace/tools
10+
RUN go mod download && \
11+
go build -o rbac-validator rbac-validator.go
12+
13+
# Main stage
414
FROM registry.access.redhat.com/ubi9/ubi:latest@sha256:8851294389a8641bd6efcd60f615c69e54fb0e2216ec8259448b35e3d9a11b06
515

616
COPY --from=yq /usr/bin/yq /usr/bin/yq
717
COPY --from=oc /usr/bin/oc /usr/bin/oc
18+
COPY --from=go-builder /workspace/tools/rbac-validator /usr/local/bin/rbac-validator
19+
20+
# Ensure the binary is executable
21+
RUN chmod +x /usr/local/bin/rbac-validator
822

923
RUN dnf -y install git \
1024
ruby \
@@ -20,7 +34,6 @@ COPY requirements.txt ./
2034

2135
RUN pip3 install -r requirements.txt
2236

23-
2437
# Because Cachi2 doesn't support ruby, we've got to gem install it for now
2538
# Can look into building it from source later, although without prefetch
2639
# not much more secure

README.md

Lines changed: 98 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,106 @@
11
# konflux-release-data-ci
2-
Config for building CI worker image for konflux-release-data repo
2+
3+
Config for building CI worker image for konflux-release-data repo, including RBAC validation tools.
4+
5+
## Overview
6+
7+
This repository provides:
8+
- CI worker image configuration for the konflux-release-data repository
9+
- RBAC validation tools using Kubernetes' official validation library
10+
- Development tooling for RBAC policy verification
11+
12+
## RBAC Validator Tool
13+
14+
The `tools/` directory contains a Go-based RBAC validator that uses Kubernetes' official validation logic to verify RBAC policy subsets.
15+
16+
### Purpose
17+
18+
The RBAC validator ensures that user-defined roles and permissions are proper subsets of reference roles, preventing privilege escalation in Konflux tenants. It validates that:
19+
20+
- User roles don't exceed the permissions granted by reference roles
21+
- APIGroups, Resources, Verbs, and ResourceNames are properly constrained
22+
- Multi-rule policies are comprehensively validated
23+
24+
### Components
25+
26+
#### `tools/rbac-validator.go`
27+
Main Go binary that:
28+
- Accepts JSON input with user rules and reference rules
29+
- Uses `k8s.io/component-helpers/auth/rbac/validation.Covers()` for authoritative validation
30+
- Returns JSON output indicating whether user rules are covered by reference rules
31+
- Handles errors gracefully with structured error responses
32+
33+
#### `tools/rbac-validator_test.go`
34+
Comprehensive test suite with:
35+
- **Edge case validation**: APIGroups overlap, subresources, resourceNames constraints
36+
- **Real-world Konflux scenarios**: contributor vs admin roles, release pipeline permissions
37+
- **Binary integration tests**: End-to-end validation of JSON input/output
38+
- **Error handling tests**: Invalid JSON and malformed input validation
39+
40+
#### `tools/Makefile`
41+
Development workflow automation:
42+
```bash
43+
make build # Build the binary
44+
make test # Run all tests
45+
make fmt # Format Go code
46+
make lint # Run golangci-lint
47+
make check-fmt # Verify code formatting
48+
make ci # Run full CI pipeline (format check, lint, test, build)
49+
```
50+
51+
#### `tools/.golangci.yml`
52+
Linting configuration with security and code quality checks.
53+
54+
### Integration
55+
56+
The validator is integrated into the CI container and used by tenant validation scripts:
57+
58+
1. **CI Container**: Binary is pre-built during container image creation
59+
2. **Smart Discovery**: Python scripts automatically find the binary via:
60+
- PATH lookup for CI environments
61+
- Local repository build for development
62+
- On-demand compilation as fallback
63+
3. **Tenant Validation**: Used by `tenants-config/tests/` for validating production and staging tenant roles
64+
65+
### Development Workflow
66+
67+
#### Local Development
68+
```bash
69+
cd tools/
70+
make install-tools # Install golangci-lint
71+
make ci # Run full validation pipeline
72+
```
73+
74+
#### Adding Test Cases
75+
Test cases should cover:
76+
- Real Konflux role scenarios from infra-deployments
77+
- Edge cases for RBAC validation behavior
78+
- Error conditions and malformed input
79+
80+
#### Binary Usage
81+
```bash
82+
echo '{"userRules": [...], "referenceRules": [...]}' | ./rbac-validator
83+
```
84+
85+
### Dependencies
86+
87+
- Go 1.22+
88+
- `k8s.io/api` v0.30.0
89+
- `k8s.io/component-helpers` v0.30.0
90+
- golangci-lint (for development)
91+
92+
## CI Worker Image
93+
94+
The main CI worker image includes:
95+
- Python environment with tox support
96+
- Go toolchain for RBAC validator
97+
- Pre-built RBAC validator binary
98+
- Development tools and dependencies
399

4100
## TODO - Need
5101
* Fix SBOM issues related to the ruby gem install
6102
* Ensure existing CI tests can run in this image
7-
* Try running mkdocs CI jobs and update image as necssesary
103+
* Try running mkdocs CI jobs and update image as necessary
8104

9105
## TODO - Should Do
10106
* Convert to UBI

rpms.in.yaml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ packages:
1212
- python3-pip
1313
- diffutils
1414
- krb5-devel
15+
- golang
1516

1617
arches:
1718
- x86_64

0 commit comments

Comments
 (0)