Using gcr.io/google_containers/nginx-ingress-controller:0.9.0-beta.7 the nginx-controller needs to handle leader-election via configmaps. To perform the leader-election the nginx-controller needs to have the appropiate RBAC permissions. Previously to this fix, the following errors occured: - cannot get configmaps in the namespace "NAMESPACE_PLACEHOLDER". (get configmaps ingress-controller-leader-nginx) - initially creating leader election record: User "system:serviceaccount:NAMESPACE_PLACEHOLDER" cannot create configmaps in the namespace "NAMESPACE_PLACEHOLDER". (post configmaps) fix ingress rbac roles There was 2 things that the current IC (0.9 beta7) needs. The ClusterRole was missing `get nodes`: ``` RBAC DENY: user "system:serviceaccount:kube-system:nginx-ingress-controller" groups [system:serviceaccounts system:serviceaccounts:kube-system system:authenticated] cannot "get" resource "nodes" named "xxx" cluster-wide ``` The Role was missing `update configmaps`: ```RBAC DENY: user "system:serviceaccount:kube-system:nginx-ingress-controller" groups [system:serviceaccounts system:serviceaccounts:kube-system system:authenticated] cannot "update" resource "configmaps" named "ingress-controller-leader-nginx" in namespace "kube-system"``` removed update configmap because of #798 rebased on master, moved get nodes to own rule added get nodes to cluster permissions |
||
|---|---|---|
| .. | ||
| nginx-ingress-controller-rbac.yml | ||
| README.md | ||
Role Based Access Control
This example demontrates how to apply role based access control
Overview
This example applies to nginx-ingress-controllers being deployed in an environment with RBAC enabled.
Role Based Access Control is comprised of four layers:
ClusterRole- permissions assigned to a role that apply to an entire clusterClusterRoleBinding- binding a ClusterRole to a specific accountRole- permissions assigned to a role that apply to a specific namespaceRoleBinding- binding a Role to a specific account
In order for RBAC to be applied to an nginx-ingress-controller, that controller
should be assigned to a ServiceAccount. That ServiceAccount should be
bound to the Roles and ClusterRoles defined for the
nginx-ingress-controller.
Service Accounts created in this example
One ServiceAccount is created in this example, nginx-ingress-serviceaccount.
Permissions Granted in this example
There are two sets of permissions defined in this example. Cluster-wide
permissions defined by the ClusterRole named nginx-ingress-clusterrole, and
namespace specific permissions defined by the Role named
nginx-ingress-role.
Cluster Permissions
These permissions are granted in order for the nginx-ingress-controller to be
able to function as an ingress across the cluster. These permissions are
granted to the ClusterRole named nginx-ingress-clusterrole
configmaps,endpoints,nodes,pods,secrets: list, watchnodes: getservices,ingresses: get, list, watchevents: create, patchingresses/status: update
Namespace Permissions
These permissions are granted specific to the nginx-ingress namespace. These
permissions are granted to the Role named nginx-ingress-role
configmaps,pods,secrets: getendpoints: create, get, update
Furthermore to support leader-election, the nginx-ingress-controller needs to
have access to a configmap using the resourceName ingress-controller-leader-nginx
configmaps: create, get, update (for resourceNameingress-controller-leader-nginx)
This resourceName is the concatenation of the election-id and the
ingress-class as defined by the ingress-controller, which default to:
election-id:ingress-controller-leaderingress-class:nginxresourceName:<election-id>-<ingress-class>
Please adapt accordingly if you overwrite either parameter when launching the nginx-ingress-controller.
Bindings
The ServiceAccount nginx-ingress-serviceaccount is bound to the Role
nginx-ingress-role and the ClusterRole nginx-ingress-clusterrole.
Namespace created in this example
The Namespace named nginx-ingress is defined in this example. The
namespace name can be changed arbitrarily as long as all of the references
change as well.
Usage
- Create the
Namespace,Service Account,ClusterRole,Role,ClusterRoleBinding, andRoleBinding.
kubectl create -f ./nginx-ingress-controller-rbac.yml
- Create the nginx-ingress-controller
For this example to work, the Service must be in the nginx-ingress namespace:
apiVersion: v1
kind: Service
metadata:
name: nginx-ingress
namespace: nginx-ingress #match namespace of service account and role
spec:
type: LoadBalancer
ports:
- port: 80
name: http
- port: 443
name: https
selector:
k8s-app: nginx-ingress-lb
The serviceAccountName associated with the containers in the deployment must match the serviceAccount from nginx-ingress-controller-rbac.yml The namespace references in the Deployment metadata, container arguments, and POD_NAMESPACE should be in the nginx-ingress namespace.
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
name: nginx-ingress-controller
#match namespace of service account and role
namespace: nginx-ingress
spec:
replicas: 2
template:
metadata:
labels:
k8s-app: nginx-ingress-lb
spec:
#match name of service account
serviceAccountName: nginx-ingress-serviceaccount
containers:
- name: nginx-ingress-controller
image: gcr.io/google_containers/nginx-ingress-controller:version
#namespace matching is required in some arguments
args:
- /nginx-ingress-controller
- --default-backend-service=default/default-http-backend
- --default-ssl-certificate=$(POD_NAMESPACE)/tls-certificate
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
#match namespace of service account and role
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
ports:
- containerPort: 80
- containerPort: 443