suite: RBAC configuration
templates:
  - clusterrole.yaml
  - clusterrolebinding.yaml
  - serviceaccount.yaml
release:
  name: rbac
tests:
  - it: should create default RBAC related objects
    asserts:
      - isKind:
          of: ClusterRole
        template: clusterrole.yaml
      - equal:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      - isKind:
          of: ClusterRoleBinding
        template: clusterrolebinding.yaml
      - equal:
          path: metadata.name
          value: rbac-external-dns-viewer
        template: clusterrolebinding.yaml
      - isKind:
          of: ServiceAccount
        template: serviceaccount.yaml
      - equal:
          path: metadata.name
          value: rbac-external-dns
        template: serviceaccount.yaml

  - it: should create default RBAC rules
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: [""]
              resources: ["nodes"]
              verbs: ["list", "watch"]
            - apiGroups: [""]
              resources: ["pods"]
              verbs: ["get", "watch", "list"]
            - apiGroups: [""]
              resources: ["services"]
              verbs: ["get","watch","list"]
            - apiGroups: ["discovery.k8s.io"]
              resources: ["endpointslices"]
              verbs: ["get","watch","list"]
            - apiGroups: ["extensions","networking.k8s.io"]
              resources: ["ingresses"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'ambassador-host'
    set:
      sources:
        - ambassador-host
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["getambassador.io"]
              resources: ["hosts","ingresses"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'crd' and 'traefik-proxy'
    set:
      sources:
        - crd
        - traefik-proxy
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["externaldns.k8s.io"]
              resources: ["dnsendpoints"]
              verbs: ["get","watch","list"]
            - apiGroups: ["externaldns.k8s.io"]
              resources: ["dnsendpoints/status"]
              verbs: ["*"]
            - apiGroups: ["traefik.containo.us", "traefik.io"]
              resources: ["ingressroutes", "ingressroutetcps", "ingressrouteudps"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'f5' when 'f5-virtualserver' is set
    set:
      sources:
        - f5-virtualserver
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["cis.f5.com"]
              resources: ["virtualservers", "transportservers"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'f5' when 'f5-transportserver' is set
    set:
      sources:
        - f5-transportserver
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["cis.f5.com"]
              resources: ["virtualservers", "transportservers"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'gateway-api' with source 'gateway-httproute'
    set:
      sources:
        - gateway-httproute
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["gateways"]
              verbs: ["get","watch","list"]
            - apiGroups: [""]
              resources: ["namespaces"]
              verbs: ["get","watch","list"]
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["httproutes"]
              verbs: ["get","watch","list"]

  - it: should create default RBAC rules for 'gateway-api' with sources 'tlsroute,tcproute,udproute'
    set:
      sources:
        - gateway-tlsroute
        - gateway-tcproute
        - gateway-udproute
    asserts:
      - template: clusterrole.yaml
        equal:
          path: rules
          value:
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["gateways"]
              verbs: ["get","watch","list"]
            - apiGroups: [""]
              resources: ["namespaces"]
              verbs: ["get","watch","list"]
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["tlsroutes"]
              verbs: ["get","watch","list"]
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["tcproutes"]
              verbs: ["get","watch","list"]
            - apiGroups: ["gateway.networking.k8s.io"]
              resources: ["udproutes"]
              verbs: ["get","watch","list"]

  - it: should create Role instead of ClusterRole when namespaced is true
    set:
      namespaced: true
      sources:
        - service
    asserts:
      - isKind:
          of: Role
        template: clusterrole.yaml
      - equal:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml

  - it: should create RoleBinding instead of ClusterRoleBinding when namespaced is true
    set:
      namespaced: true
      sources:
        - service
    asserts:
      - isKind:
          of: RoleBinding
        template: clusterrolebinding.yaml
      - equal:
          path: metadata.name
          value: rbac-external-dns-viewer
        template: clusterrolebinding.yaml

  - it: should create all required resources when namespaced=true and gatewayNamespace is specified
    set:
      namespaced: true
      gatewayNamespace: gateway-ns
      sources:
        - gateway-httproute
    asserts:
      # Should have: main Role + ClusterRole for namespaces + Gateway Role
      - hasDocuments:
          count: 3
        template: clusterrole.yaml
      - hasDocuments:
          count: 3
        template: clusterrolebinding.yaml

      # Main role should exist and contain route permissions but NOT gateway permissions
      - isKind:
          of: Role
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["httproutes"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      - notContains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["gateways"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml

      # ClusterRole for namespaces should exist
      - isKind:
          of: ClusterRole
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-namespaces
        template: clusterrole.yaml

      # Gateway role should exist and have gateway permissions only
      - isKind:
          of: Role
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-gateway
        template: clusterrole.yaml
      - equal:
          path: metadata.namespace
          value: gateway-ns
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-gateway
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["gateways"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-gateway
        template: clusterrole.yaml


  - it: should create main Role with gateway permissions and ClusterRole for namespaces when namespaced=true and gatewayNamespace is not set
    set:
      namespaced: true
      sources:
        - gateway-httproute
    asserts:
      # Should have: main Role + ClusterRole for namespaces
      - hasDocuments:
          count: 2
        template: clusterrole.yaml
      - hasDocuments:
          count: 2
        template: clusterrolebinding.yaml
      # Main Role should exist and contain gateway permissions
      - isKind:
          of: Role
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["gateways"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["httproutes"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns
        template: clusterrole.yaml
      # ClusterRole for namespaces should exist
      - isKind:
          of: ClusterRole
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-namespaces
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: [""]
            resources: ["namespaces"]
            verbs: ["get","watch","list"]
        documentSelector:
          path: metadata.name
          value: rbac-external-dns-namespaces
        template: clusterrole.yaml

  - it: should create ClusterRole with all permissions when namespaced=false and gateway sources exist
    set:
      namespaced: false
      sources:
        - gateway-httproute
    asserts:
      - hasDocuments:
          count: 1
        template: clusterrole.yaml
      - hasDocuments:
          count: 1
        template: clusterrolebinding.yaml
      - isKind:
          of: ClusterRole
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
            resources: ["gateways"]
            verbs: ["get","watch","list"]
        template: clusterrole.yaml
      - contains:
          path: rules
          content:
            apiGroups: [""]
            resources: ["namespaces"]
            verbs: ["get","watch","list"]
        template: clusterrole.yaml

  - it: should create only ClusterRole when namespaced=false and no gateway sources
    set:
      namespaced: false
      sources:
        - service
        - ingress
    asserts:
      - hasDocuments:
          count: 1
        template: clusterrole.yaml
      - hasDocuments:
          count: 1
        template: clusterrolebinding.yaml
      - isKind:
          of: ClusterRole
        template: clusterrole.yaml
      - notContains:
          path: rules
          content:
            apiGroups: ["gateway.networking.k8s.io"]
        template: clusterrole.yaml

  - it: should create only Role when namespaced=true and no gateway sources
    set:
      namespaced: true
      sources:
        - service
        - ingress
    asserts:
      - hasDocuments:
          count: 1
        template: clusterrole.yaml
      - hasDocuments:
          count: 1
        template: clusterrolebinding.yaml
      - isKind:
          of: Role
        template: clusterrole.yaml
      - isKind:
          of: RoleBinding
        template: clusterrolebinding.yaml
