Skip to content

RBAC Permissions Guide

This guide details all Kubernetes RBAC permissions required by the e6data operator and its managed components.


Overview

The e6data deployment consists of multiple components, each requiring specific RBAC permissions:

Component Scope Purpose
E6 Operator Cluster-wide Manages all CRDs and workloads
E6Console Cluster-wide Web UI and API server for managing E6Data resources
Engine Components Namespace MetadataServices, QueryService workloads
Monitoring Components Namespace or Cluster Vector and Telegraf log/metrics collection
GreptimeDB Namespace Time-series database for query history

Quick Start: Complete Workspace RBAC Template

Copy and apply this template to set up RBAC for a new workspace. Replace <WORKSPACE_NAME> with your workspace name (e.g., workspace1).

# workspace-rbac.yaml
# Complete RBAC setup for e6data workspace
# Replace <WORKSPACE_NAME> with your workspace name

---
# 1. Create Namespace
apiVersion: v1
kind: Namespace
metadata:
  name: <WORKSPACE_NAME>

---
# 2. Engine ServiceAccount (for MetadataServices, QueryService, TrafficInfra)
apiVersion: v1
kind: ServiceAccount
metadata:
  name: <WORKSPACE_NAME>-engine
  namespace: <WORKSPACE_NAME>

---
# 3. Engine Role (Namespace-scoped permissions)
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: <WORKSPACE_NAME>-engine-role
  namespace: <WORKSPACE_NAME>
rules:
  # Pod status (read-only, operator manages pods)
  - apiGroups: [""]
    resources: ["pods", "pods/status", "endpoints"]
    verbs: ["get", "list", "watch"]
  # Events (emit events for observability)
  - apiGroups: [""]
    resources: ["events"]
    verbs: ["get", "list", "watch", "create", "patch"]
  # Service discovery
  - apiGroups: [""]
    resources: ["services"]
    verbs: ["get", "list", "watch"]
  # Deployment status (read-only, operator handles scaling)
  - apiGroups: ["apps"]
    resources: ["deployments", "deployments/status", "replicasets", "replicasets/status"]
    verbs: ["get", "list", "watch"]
  # Governance policies (for policy enforcement)
  - apiGroups: ["e6data.io"]
    resources: ["governances"]
    verbs: ["get", "list", "watch"]

---
# 4. Engine RoleBinding
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: <WORKSPACE_NAME>-engine-role-binding
  namespace: <WORKSPACE_NAME>
subjects:
  - kind: ServiceAccount
    name: <WORKSPACE_NAME>-engine
    namespace: <WORKSPACE_NAME>
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: <WORKSPACE_NAME>-engine-role

---
# 5. Monitoring ServiceAccount (for Vector/Telegraf)
apiVersion: v1
kind: ServiceAccount
metadata:
  name: <WORKSPACE_NAME>-monitoring
  namespace: <WORKSPACE_NAME>

---
# 6. Monitoring ClusterRole (can be shared across workspaces)
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: <WORKSPACE_NAME>-monitoring-role
rules:
  # Pod/service discovery and metrics
  - apiGroups: [""]
    resources: ["nodes", "nodes/proxy", "services", "endpoints", "pods", "events"]
    verbs: ["get", "list", "watch"]
  # Deployment tracking
  - apiGroups: ["apps"]
    resources: ["replicasets"]
    verbs: ["get", "list", "watch"]
  # Prometheus metrics scraping
  - nonResourceURLs: ["/metrics"]
    verbs: ["get"]

---
# 7. Monitoring ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: <WORKSPACE_NAME>-monitoring-role-binding
subjects:
  - kind: ServiceAccount
    name: <WORKSPACE_NAME>-monitoring
    namespace: <WORKSPACE_NAME>
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: <WORKSPACE_NAME>-monitoring-role

Apply the Template

# Option 1: Apply with sed substitution
sed 's/<WORKSPACE_NAME>/workspace1/g' workspace-rbac.yaml | kubectl apply -f -

# Option 2: Apply directly and then patch
kubectl apply -f workspace-rbac.yaml

Naming Convention

Component Naming Pattern Example
Namespace <workspace> workspace1
Engine ServiceAccount <workspace>-engine workspace1-engine
Monitoring ServiceAccount <workspace>-monitoring workspace1-monitoring
Engine Role <workspace>-engine-role workspace1-engine-role
Monitoring ClusterRole <workspace>-monitoring-role workspace1-monitoring-role

Reference in NamespaceConfig

After applying RBAC, reference the service accounts in your NamespaceConfig:

apiVersion: e6data.io/v1alpha1
kind: NamespaceConfig
metadata:
  name: workspace1-config
  namespace: workspace1
spec:
  cloud: AWS
  imagePullSecrets:
    - gcr-key
  karpenterNodePool: workspace1-nodepool
  serviceAccounts:
    data: workspace1-engine          # <-- Engine ServiceAccount
    monitoring: workspace1-monitoring # <-- Monitoring ServiceAccount
  storageBackend: s3a://e6-workspace1-metadata

1. E6 Operator RBAC

The operator requires the most extensive permissions as it creates and manages all other resources.

1.1 Cluster-Wide Permissions

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: e6-operator
rules:
  # Node access for cloud provider detection
  - apiGroups: [""]
    resources: ["nodes"]
    verbs: ["get", "list", "watch"]

  # Namespace discovery
  - apiGroups: [""]
    resources: ["namespaces"]
    verbs: ["get", "list", "watch"]

  # e6data CRDs - full control
  - apiGroups: ["e6data.io"]
    resources:
      - metadataservices
      - metadataservices/status
      - metadataservices/finalizers
      - queryservices
      - queryservices/status
      - queryservices/finalizers
      - trafficinfras
      - trafficinfras/status
      - trafficinfras/finalizers
      - authgateways
      - authgateways/status
      - authgateways/finalizers
      - e6consoles
      - e6consoles/status
      - e6consoles/finalizers
      - e6catalogs
      - e6catalogs/status
      - e6catalogs/finalizers
      - catalogrefreshes
      - catalogrefreshes/status
      - catalogrefreshes/finalizers
      - catalogrefreshschedules
      - catalogrefreshschedules/status
      - catalogrefreshschedules/finalizers
      - pools
      - pools/status
      - pools/finalizers
      - governances
      - governances/status
      - governances/finalizers
      - namespaceconfigs
      - namespaceconfigs/status
      - namespaceconfigs/finalizers
      - monitoringservices
      - monitoringservices/status
      - monitoringservices/finalizers
      - greptimedbclusters
      - greptimedbclusters/status
      - greptimedbclusters/finalizers
    verbs: ["*"]

  # E6Console RBAC management (for console's ClusterRole/ClusterRoleBinding)
  - apiGroups: ["rbac.authorization.k8s.io"]
    resources: ["clusterroles", "clusterrolebindings"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # ServiceAccount management for E6Console
  - apiGroups: [""]
    resources: ["serviceaccounts"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Ingress management for E6Console
  - apiGroups: ["networking.k8s.io"]
    resources: ["ingresses"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Karpenter integration (optional, when karpenter.enabled=true)
  - apiGroups: ["karpenter.sh"]
    resources: ["nodepools"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]
  - apiGroups: ["karpenter.k8s.aws"]
    resources: ["ec2nodeclasses"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]
  - apiGroups: ["karpenter.azure.com"]
    resources: ["aksnodeclasses"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]
  - apiGroups: ["karpenter.gcp.sh"]
    resources: ["gcpnodeclasses"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # GreptimeDB Operator CRDs (optional, when using MonitoringServices)
  - apiGroups: ["greptime.io"]
    resources:
      - greptimedbclusters
      - greptimedbclusters/status
    verbs: ["*"]

1.2 Namespace-Scoped Permissions

These permissions are applied to all namespaces where e6data workloads run:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: e6-operator-workloads
rules:
  # Core workload management
  - apiGroups: [""]
    resources:
      - pods
      - pods/log
      - pods/status
    verbs: ["get", "list", "watch", "delete"]

  - apiGroups: [""]
    resources:
      - services
      - endpoints
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  - apiGroups: [""]
    resources:
      - configmaps
      - secrets
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  - apiGroups: [""]
    resources:
      - serviceaccounts
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  - apiGroups: [""]
    resources:
      - persistentvolumeclaims
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Workload controllers
  - apiGroups: ["apps"]
    resources:
      - deployments
      - deployments/status
      - deployments/scale
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  - apiGroups: ["apps"]
    resources:
      - daemonsets
      - daemonsets/status
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  - apiGroups: ["apps"]
    resources:
      - statefulsets
      - statefulsets/status
      - statefulsets/scale
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # RBAC management (for auto-created service accounts)
  - apiGroups: ["rbac.authorization.k8s.io"]
    resources:
      - roles
      - rolebindings
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Events (for status reporting)
  - apiGroups: [""]
    resources:
      - events
    verbs: ["create", "patch"]

  # Autoscaling (for HPA integration)
  - apiGroups: ["autoscaling"]
    resources:
      - horizontalpodautoscalers
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Pod Disruption Budgets
  - apiGroups: ["policy"]
    resources:
      - poddisruptionbudgets
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

1.3 Complete Operator ClusterRole

Combined ClusterRole for the operator:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: e6-operator
  labels:
    app.kubernetes.io/name: e6-operator
    app.kubernetes.io/component: controller
rules:
  # Cloud provider detection
  - apiGroups: [""]
    resources: ["nodes"]
    verbs: ["get", "list", "watch"]

  # Namespace access
  - apiGroups: [""]
    resources: ["namespaces"]
    verbs: ["get", "list", "watch"]

  # All e6data CRDs
  - apiGroups: ["e6data.io"]
    resources: ["*"]
    verbs: ["*"]

  # GreptimeDB CRDs
  - apiGroups: ["greptime.io"]
    resources: ["*"]
    verbs: ["*"]

  # Core resources
  - apiGroups: [""]
    resources:
      - pods
      - pods/log
      - pods/status
      - services
      - endpoints
      - configmaps
      - secrets
      - serviceaccounts
      - persistentvolumeclaims
      - events
    verbs: ["*"]

  # Workload controllers
  - apiGroups: ["apps"]
    resources:
      - deployments
      - daemonsets
      - statefulsets
    verbs: ["*"]

  # RBAC
  - apiGroups: ["rbac.authorization.k8s.io"]
    resources:
      - roles
      - rolebindings
      - clusterroles
      - clusterrolebindings
    verbs: ["*"]

  # Autoscaling
  - apiGroups: ["autoscaling"]
    resources: ["horizontalpodautoscalers"]
    verbs: ["*"]

  # Policy
  - apiGroups: ["policy"]
    resources: ["poddisruptionbudgets"]
    verbs: ["*"]

  # Karpenter (optional)
  - apiGroups: ["karpenter.sh"]
    resources: ["nodepools"]
    verbs: ["*"]
  - apiGroups: ["karpenter.k8s.aws"]
    resources: ["ec2nodeclasses"]
    verbs: ["*"]
  - apiGroups: ["karpenter.azure.com"]
    resources: ["aksnodeclasses"]
    verbs: ["*"]
  - apiGroups: ["karpenter.gcp.sh"]
    resources: ["gcpnodeclasses"]
    verbs: ["*"]

  # Leader election
  - apiGroups: ["coordination.k8s.io"]
    resources: ["leases"]
    verbs: ["*"]

  # Admission webhooks
  - apiGroups: ["admissionregistration.k8s.io"]
    resources:
      - validatingwebhookconfigurations
      - mutatingwebhookconfigurations
    verbs: ["get", "list", "watch"]

1.4 ClusterRoleBinding

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: e6-operator
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: e6-operator
subjects:
  - kind: ServiceAccount
    name: e6-operator
    namespace: e6-operator-system

1.5 E6Console RBAC (Auto-Created)

When you create an E6Console CR, the operator automatically creates a ClusterRole and ClusterRoleBinding for the console's service account. This allows the console UI/API to manage E6Data resources.

Auto-created ClusterRole:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: {console-name}-console-{namespace}  # e.g., console-console-poc1
rules:
  # Full access to all E6Data CRDs
  - apiGroups: ["e6data.io"]
    resources: ["*"]
    verbs: ["get", "list", "watch", "create", "update", "patch", "delete"]

  # Read-only access to core Kubernetes resources
  - apiGroups: [""]
    resources: ["namespaces", "secrets", "configmaps", "pods", "services"]
    verbs: ["get", "list", "watch"]

  # Read-only access to workload controllers
  - apiGroups: ["apps"]
    resources: ["deployments", "statefulsets"]
    verbs: ["get", "list", "watch"]

Auto-created ClusterRoleBinding:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: {console-name}-console-{namespace}
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: {console-name}-console-{namespace}
subjects:
  - kind: ServiceAccount
    name: {console-name}-console
    namespace: {namespace}

2. Engine Components RBAC

Engine components (MetadataServices, QueryService pods) run in workspace namespaces and need specific permissions for autoscaling and service discovery.

2.1 Engine Role (Data ServiceAccount)

The engine ServiceAccount (dataServiceAccount in NamespaceConfig) is used by MetadataServices, QueryService pods, and TrafficInfra components (xDS/Envoy). It requires the following namespace-scoped Role:

---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: e6data-data  # or your custom name from NamespaceConfig.spec.serviceAccounts.data
  namespace: <YOUR_NAMESPACE>
  annotations:
    # AWS IRSA (for S3 access)
    eks.amazonaws.com/role-arn: "arn:aws:iam::ACCOUNT:role/e6data-role"
    # GCP Workload Identity (for GCS access)
    iam.gke.io/gcp-service-account: "e6data@PROJECT.iam.gserviceaccount.com"
    # Azure Workload Identity (for Azure Blob access)
    azure.workload.identity/client-id: "CLIENT_ID"
  labels:
    azure.workload.identity/use: "true"  # Azure only
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: e6data-engine-role
  namespace: <YOUR_NAMESPACE>
rules:
  # Pod status - read only (operator manages pods)
  - apiGroups: [""]
    resources:
      - pods
      - pods/status
    verbs:
      - get
      - list
      - watch

  # Events - for emitting component events
  - apiGroups: [""]
    resources:
      - events
    verbs:
      - get
      - list
      - watch
      - create
      - patch

  # Services - for service discovery (xDS, planner, executor)
  - apiGroups: [""]
    resources:
      - services
    verbs:
      - get
      - list
      - watch

  # Endpoints - for xDS/Envoy service discovery of planner headless services
  - apiGroups: [""]
    resources:
      - endpoints
    verbs:
      - get
      - list
      - watch

  # EndpointSlices - for xDS/Envoy service discovery (K8s 1.21+)
  - apiGroups: ["discovery.k8s.io"]
    resources:
      - endpointslices
    verbs:
      - get
      - list
      - watch

  # Deployments and ReplicaSets - read only (operator handles scaling via API)
  - apiGroups: ["apps"]
    resources:
      - deployments
      - deployments/status
      - replicasets
      - replicasets/status
    verbs:
      - get
      - list
      - watch

  # ConfigMaps - for xDS configuration and Envoy bootstrap
  - apiGroups: [""]
    resources:
      - configmaps
    verbs:
      - get
      - list
      - watch

  # Secrets - for TLS certificates (Envoy/Pomerium)
  - apiGroups: [""]
    resources:
      - secrets
    verbs:
      - get
      - list
      - watch
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: e6data-engine-role-binding
  namespace: <YOUR_NAMESPACE>
subjects:
  - kind: ServiceAccount
    name: e6data-data
    namespace: <YOUR_NAMESPACE>
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: e6data-engine-role

Key Permissions Explained: - pods, pods/status: Read-only access for checking pod health and status - events: Create/patch for emitting component events (e.g., "Query started", "Scaling requested") - services: Required for service discovery between components - endpoints, endpointslices: Required for xDS to discover planner pod endpoints for Envoy routing - deployments, replicasets: Read-only for status checks (operator handles scaling via its HTTP API on port 8082) - configmaps: Required for xDS configuration and Envoy bootstrap config - secrets: Required for TLS certificates when using Envoy or Pomerium with TLS

2.2 Storage and Schema Services

Storage and Schema services use the same e6data-data ServiceAccount. In addition to K8s RBAC, they need cloud IAM permissions for storage access:

Cloud Mechanism Annotation
AWS IRSA or Pod Identity eks.amazonaws.com/role-arn
GCP Workload Identity iam.gke.io/gcp-service-account
Azure Workload Identity azure.workload.identity/client-id
Linode/Other Environment Variables Use commonEnvVars in NamespaceConfig

For platforms without IAM roles (e.g., Linode):

Set AWS credentials via NamespaceConfig:

apiVersion: e6data.io/v1alpha1
kind: NamespaceConfig
metadata:
  name: my-workspace
  namespace: demo
spec:
  cloud: AWS
  storageBackend: s3a://my-bucket
  serviceAccounts:
    data: e6data-data
    monitoring: e6data-monitoring
  commonEnvVars:
    AWS_ACCESS_KEY_ID: "AKIA..."
    AWS_SECRET_ACCESS_KEY: "..."
    AWS_REGION: "us-east-1"

2.3 Complete Engine RBAC Example

Here's a complete example for setting up engine RBAC in a namespace (includes permissions for xDS/Envoy):

# 1. Create the namespace
apiVersion: v1
kind: Namespace
metadata:
  name: workspace-prod
---
# 2. Create ServiceAccount with cloud annotations
apiVersion: v1
kind: ServiceAccount
metadata:
  name: e6data-data
  namespace: workspace-prod
  annotations:
    # Choose based on your cloud:
    eks.amazonaws.com/role-arn: "arn:aws:iam::123456789012:role/e6data-workspace-prod"
---
# 3. Create Role (includes xDS/Envoy permissions)
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: e6data-engine-role
  namespace: workspace-prod
rules:
  # Pod status - read only (operator manages pods)
  - apiGroups: [""]
    resources: ["pods", "pods/status"]
    verbs: ["get", "list", "watch"]
  # Events - create/patch for emitting events
  - apiGroups: [""]
    resources: ["events"]
    verbs: ["get", "list", "watch", "create", "patch"]
  # Service discovery (planner, executor, xDS)
  - apiGroups: [""]
    resources: ["services"]
    verbs: ["get", "list", "watch"]
  # Endpoints for xDS/Envoy service discovery
  - apiGroups: [""]
    resources: ["endpoints"]
    verbs: ["get", "list", "watch"]
  - apiGroups: ["discovery.k8s.io"]
    resources: ["endpointslices"]
    verbs: ["get", "list", "watch"]
  # Deployment status - read only (operator handles scaling via its API)
  - apiGroups: ["apps"]
    resources: ["deployments", "deployments/status", "replicasets", "replicasets/status"]
    verbs: ["get", "list", "watch"]
  # ConfigMaps for xDS config and Envoy bootstrap
  - apiGroups: [""]
    resources: ["configmaps"]
    verbs: ["get", "list", "watch"]
  # Secrets for TLS (Envoy/Pomerium)
  - apiGroups: [""]
    resources: ["secrets"]
    verbs: ["get", "list", "watch"]
---
# 4. Bind Role to ServiceAccount
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: e6data-engine-role-binding
  namespace: workspace-prod
subjects:
  - kind: ServiceAccount
    name: e6data-data
    namespace: workspace-prod
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: e6data-engine-role

3. Monitoring Components RBAC

Monitoring components need cluster-scoped permissions to discover and scrape pods across namespaces.

3.1 Monitoring Agent ClusterRole (e6data-agent)

The monitoring ServiceAccount (monitoringServiceAccount in NamespaceConfig) is used by Vector/Telegraf for metrics and log collection. It requires a ClusterRole because it needs to discover pods across all namespaces:

---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: e6data-monitoring  # or your custom name from NamespaceConfig.spec.serviceAccounts.monitoring
  namespace: <YOUR_NAMESPACE>
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: e6data-monitoring-role
rules:
  # Core resources - for service/pod discovery and metrics collection
  - apiGroups: [""]
    resources:
      - nodes
      - nodes/proxy
      - services
      - endpoints
      - pods
      - events
    verbs:
      - get
      - list
      - watch

  # ReplicaSets - for deployment tracking
  - apiGroups: ["apps"]
    resources:
      - replicasets
    verbs:
      - get
      - list
      - watch

  # Non-resource URLs - for scraping /metrics endpoints
  - nonResourceURLs:
      - /metrics
    verbs:
      - get
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: e6data-monitoring-role-binding-<YOUR_NAMESPACE>
subjects:
  - kind: ServiceAccount
    name: e6data-monitoring
    namespace: <YOUR_NAMESPACE>
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: e6data-monitoring-role

Key Permissions Explained: - nodes, nodes/proxy: Required for node-level metrics (CPU, memory, disk) - services, endpoints, pods: Required for discovering pods to scrape - events: Required for event collection and alerting - replicasets: Required for deployment status tracking - /metrics: Required for scraping Prometheus metrics endpoints

3.2 Complete Monitoring RBAC Example

Here's a complete example for setting up monitoring RBAC:

# 1. Create ServiceAccount
apiVersion: v1
kind: ServiceAccount
metadata:
  name: e6data-monitoring
  namespace: workspace-prod
---
# 2. Create ClusterRole (can be shared across namespaces)
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: e6data-monitoring-role
rules:
  - apiGroups: [""]
    resources: ["nodes", "nodes/proxy", "services", "endpoints", "pods", "events"]
    verbs: ["get", "list", "watch"]
  - apiGroups: ["apps"]
    resources: ["replicasets"]
    verbs: ["get", "list", "watch"]
  - nonResourceURLs: ["/metrics"]
    verbs: ["get"]
---
# 3. Create ClusterRoleBinding (one per namespace)
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: e6data-monitoring-role-binding-workspace-prod
subjects:
  - kind: ServiceAccount
    name: e6data-monitoring
    namespace: workspace-prod
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: e6data-monitoring-role

3.3 Vector Logs DaemonSet (Extended)

For log collection across the cluster:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: vector-logs
rules:
  # Read pod metadata for log enrichment
  - apiGroups: [""]
    resources: ["pods", "namespaces"]
    verbs: ["get", "list", "watch"]

  # Read nodes for node-level metadata
  - apiGroups: [""]
    resources: ["nodes"]
    verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: vector-logs
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: vector-logs
subjects:
  - kind: ServiceAccount
    name: vector-logs
    namespace: monitoring-system

3.4 Vector Metrics DaemonSet (Extended)

For Prometheus metrics scraping:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: vector-metrics
rules:
  # Discover pods for scraping
  - apiGroups: [""]
    resources: ["pods", "services", "endpoints"]
    verbs: ["get", "list", "watch"]

  # Read nodes for node-level metrics
  - apiGroups: [""]
    resources: ["nodes", "nodes/metrics", "nodes/proxy"]
    verbs: ["get", "list", "watch"]

  # Access Kubernetes metrics API
  - apiGroups: ["metrics.k8s.io"]
    resources: ["pods", "nodes"]
    verbs: ["get", "list"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: vector-metrics
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: vector-metrics
subjects:
  - kind: ServiceAccount
    name: vector-metrics
    namespace: monitoring-system

3.3 Telegraf Metrics DaemonSet

For system-level metrics collection (CPU, memory, disk, network):

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: telegraf
rules:
  # Discover pods for metric annotation scraping
  - apiGroups: [""]
    resources: ["pods"]
    verbs: ["get", "list", "watch"]

  # Read nodes for node-level metrics
  - apiGroups: [""]
    resources: ["nodes", "nodes/stats", "nodes/proxy"]
    verbs: ["get", "list", "watch"]

  # Access Kubernetes API server metrics
  - apiGroups: [""]
    resources: ["services", "endpoints"]
    verbs: ["get", "list", "watch"]

  # Read namespaces for filtering
  - apiGroups: [""]
    resources: ["namespaces"]
    verbs: ["get", "list", "watch"]

  # Access metrics API for resource usage
  - apiGroups: ["metrics.k8s.io"]
    resources: ["pods", "nodes"]
    verbs: ["get", "list"]

  # Read PVCs for disk metrics (optional)
  - apiGroups: [""]
    resources: ["persistentvolumeclaims", "persistentvolumes"]
    verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: telegraf
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: telegraf
subjects:
  - kind: ServiceAccount
    name: telegraf
    namespace: monitoring-system

3.4 Telegraf with Kubernetes Input Plugin

If using the Kubernetes input plugin for cluster metrics:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: telegraf-kubernetes
rules:
  # Core API resources
  - apiGroups: [""]
    resources:
      - pods
      - nodes
      - namespaces
      - services
      - endpoints
      - persistentvolumeclaims
      - persistentvolumes
      - replicationcontrollers
      - resourcequotas
      - limitranges
    verbs: ["get", "list", "watch"]

  # Workload resources
  - apiGroups: ["apps"]
    resources:
      - deployments
      - daemonsets
      - replicasets
      - statefulsets
    verbs: ["get", "list", "watch"]

  # Batch resources
  - apiGroups: ["batch"]
    resources:
      - jobs
      - cronjobs
    verbs: ["get", "list", "watch"]

  # Autoscaling resources
  - apiGroups: ["autoscaling"]
    resources:
      - horizontalpodautoscalers
    verbs: ["get", "list", "watch"]

  # Node metrics (kubelet)
  - apiGroups: [""]
    resources: ["nodes/stats", "nodes/proxy", "nodes/metrics"]
    verbs: ["get", "list", "watch"]

  # Metrics API
  - apiGroups: ["metrics.k8s.io"]
    resources: ["pods", "nodes"]
    verbs: ["get", "list"]
---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: telegraf
  namespace: monitoring-system
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: telegraf-kubernetes
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: telegraf-kubernetes
subjects:
  - kind: ServiceAccount
    name: telegraf
    namespace: monitoring-system

3.5 Namespace-Scoped Monitoring (Optional)

If useClusterRole: false in MonitoringServices, use namespace-scoped RBAC:

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: vector-metrics
  namespace: workspace-prod
rules:
  - apiGroups: [""]
    resources: ["pods", "services", "endpoints"]
    verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: vector-metrics
  namespace: workspace-prod
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: vector-metrics
subjects:
  - kind: ServiceAccount
    name: vector-metrics
    namespace: workspace-prod

3.6 Namespace-Scoped Telegraf (Optional)

For namespace-restricted Telegraf deployments:

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: telegraf
  namespace: workspace-prod
rules:
  - apiGroups: [""]
    resources: ["pods", "services", "endpoints"]
    verbs: ["get", "list", "watch"]
  - apiGroups: ["apps"]
    resources: ["deployments", "daemonsets", "statefulsets"]
    verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: telegraf
  namespace: workspace-prod
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: telegraf
subjects:
  - kind: ServiceAccount
    name: telegraf
    namespace: workspace-prod

4. GreptimeDB Components RBAC

GreptimeDB pods need minimal Kubernetes API access.

4.1 GreptimeDB Pods

apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
  name: greptime
  namespace: greptime-system
rules:
  # Read configmaps for configuration
  - apiGroups: [""]
    resources: ["configmaps"]
    verbs: ["get", "list", "watch"]

  # Read secrets for credentials
  - apiGroups: [""]
    resources: ["secrets"]
    verbs: ["get", "list", "watch"]

  # Read pods for cluster discovery
  - apiGroups: [""]
    resources: ["pods"]
    verbs: ["get", "list", "watch"]

  # Read services for service discovery
  - apiGroups: [""]
    resources: ["services", "endpoints"]
    verbs: ["get", "list", "watch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
  name: greptime
  namespace: greptime-system
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: Role
  name: greptime
subjects:
  - kind: ServiceAccount
    name: greptime
    namespace: greptime-system

4.2 GreptimeDB Cloud Storage Access

GreptimeDB requires cloud IAM for S3/GCS/Azure Blob access:

AWS (IRSA required - Pod Identity not supported):

apiVersion: v1
kind: ServiceAccount
metadata:
  name: greptime
  namespace: greptime-system
  annotations:
    eks.amazonaws.com/role-arn: "arn:aws:iam::ACCOUNT:role/greptime-s3-role"

GCP (Workload Identity):

apiVersion: v1
kind: ServiceAccount
metadata:
  name: greptime
  namespace: greptime-system
  annotations:
    iam.gke.io/gcp-service-account: "greptime@PROJECT.iam.gserviceaccount.com"

Azure (Workload Identity):

apiVersion: v1
kind: ServiceAccount
metadata:
  name: greptime
  namespace: greptime-system
  annotations:
    azure.workload.identity/client-id: "GREPTIME_CLIENT_ID"
  labels:
    azure.workload.identity/use: "true"


5. Permission Summary by Component

5.1 Quick Reference Table

Component Scope Key Permissions Notes
E6 Operator Cluster CRDs, Deployments, ConfigMaps, Secrets, RBAC Required for all functionality
Storage Service None - Only needs cloud IAM
Schema Service None - Only needs cloud IAM
Query Planner Namespace Pods (get/list/watch) Service discovery
Query Executor Namespace Pods, Endpoints (get/list/watch) Autoscaling coordination
TrafficInfra (xDS/Envoy) Namespace Endpoints, EndpointSlices, Pods, Services Service discovery for routing
AuthGateway (Pomerium) Namespace ConfigMaps, Secrets TLS certificates, configuration
Vector Logs Cluster Pods, Namespaces, Nodes Log enrichment
Vector Metrics Cluster/NS Pods, Services, Endpoints, Nodes/metrics Prometheus scraping
Telegraf Cluster/NS Pods, Nodes, Services, Deployments, metrics API System metrics collection
GreptimeDB Namespace ConfigMaps, Secrets, Pods, Services Cluster coordination

5.2 Minimum Required Permissions

For restricted environments, here is the absolute minimum:

Operator (cannot be reduced): - Full CRD access (e6data.io/*) - Core resources: pods, services, configmaps, secrets, serviceaccounts - Apps: deployments, daemonsets - Nodes: get/list/watch (for cloud detection)

Engine Components (can run with zero K8s RBAC): - Cloud IAM for storage access - No Kubernetes API needed

Monitoring (can be namespace-scoped): - Pods: get/list/watch - Services/Endpoints: get/list/watch


6. Restricting Operator Scope

6.1 Namespace-Restricted Installation

To restrict the operator to specific namespaces:

# values.yaml
watchNamespaces:
  - workspace-prod
  - workspace-staging
  - greptime-system

rbac:
  create: true
  # Use Roles instead of ClusterRoles for namespace resources
  namespaceScoped: true

This creates Roles in each watched namespace instead of a ClusterRole.

6.2 Deny Specific Operations

To prevent certain operations:

# Deny creating Karpenter resources
rbac:
  extraRules: []
  denyRules:
    - apiGroups: ["karpenter.sh"]
      resources: ["*"]
      verbs: ["*"]

7. Auditing RBAC Usage

7.1 Check Current Permissions

# List operator permissions
kubectl auth can-i --list --as=system:serviceaccount:e6-operator-system:e6-operator

# Check specific permission
kubectl auth can-i create deployments --as=system:serviceaccount:e6-operator-system:e6-operator -n workspace-prod

7.2 Audit Log Analysis

Enable Kubernetes audit logging to track RBAC usage:

# audit-policy.yaml
apiVersion: audit.k8s.io/v1
kind: Policy
rules:
  - level: Metadata
    users:
      - system:serviceaccount:e6-operator-system:e6-operator
    verbs: ["create", "update", "patch", "delete"]