Skip to content

Instantly share code, notes, and snippets.

@denisgolius
Forked from egeneralov/README.md
Created October 25, 2019 09:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save denisgolius/b6de468b78942b28fe14bdc523a350bf to your computer and use it in GitHub Desktop.
Save denisgolius/b6de468b78942b28fe14bdc523a350bf to your computer and use it in GitHub Desktop.
Ansible configuration for limit user to its namespace, and list all namespaces in cluster (for dashboard). Can be used for provide access to stage environments for your developers.

k8s-rbac-limit-user-to-namespace.yml

Ansible configuration for limit user to its namespace, and list all namespaces in cluster (for dashboard). Can be used for provide access to stage environments for your developers.

Just ansible-playbook k8s-rbac-limit-user-to-namespace.yml -e namespace=cool-app-development and gather result from /tmp/cool-app-development.yaml

pre-requirements

You must have:

  • pip install openshift ansible on target host
  • working ~/.kube/config or /etc/kubernetes/admin.conf on target host

plan

  • will be created namespace

  • will be created RBAC rulles

  • downloaded namespace.kubeconfig.yaml.j2 to ansible controller /tmp/namespace.kubeconfig.yaml.j2

  • templated namespace.kubeconfig.yaml.j2 to first kube-master as /tmp/{{ namespace }}.yaml

    • default namespace for commands will be {{ namespace }}
  • you can copy /tmp/{{ namespace }}.yaml to /home/developer.name/.kube/config or send it via secure way.

  • please, test your new config with kubectl get ns,pods --kubeconfig=/tmp/{{ namespace }}.yaml

---
- name: "create user for {{ namespace }} and place configs to {{ output }}"
hosts: kube-master[0]
gather_facts: 'no'
vars:
namespace: egeneralov
output:
- "/tmp/{{ namespace }}.yaml"
tasks:
- k8s:
definition:
apiVersion: v1
kind: Namespace
metadata:
name: "{{ namespace }}"
state: present
name: "Create namespace {{ namespace }}"
- k8s:
definition:
apiVersion: v1
kind: ServiceAccount
metadata:
name: "{{ namespace }}-user"
namespace: "{{ namespace }}"
secrets:
- name: "{{ namespace }}-user-token"
state: present
name: "install ServiceAccount {{ namespace }}-user to {{ namespace }} namespace"
- k8s:
definition:
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: Role
metadata:
name: "{{ namespace }}-user-full-access"
namespace: "{{ namespace }}"
rules:
- apiGroups:
- ''
- extensions
- apps
- autoscaling
resources:
- '*'
verbs:
- '*'
- apiGroups:
- batch
resources:
- jobs
- cronjobs
verbs:
- '*'
state: present
name: "install Role {{ namespace }}-user-full-access to {{ namespace }} namespace"
- k8s:
definition:
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: RoleBinding
metadata:
name: "{{ namespace }}-user-view"
namespace: "{{ namespace }}"
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: "{{ namespace }}-user-full-access"
subjects:
- kind: ServiceAccount
name: "{{ namespace }}-user"
namespace: "{{ namespace }}"
state: present
name: "install RoleBinding {{ namespace }}-user-view to {{ namespace }} namespace"
- k8s:
definition:
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: "{{ namespace }}"
rules:
- apiGroups:
- admissionregistration.k8s.io
resources:
- validatingwebhookconfigurations
- mutatingwebhookconfigurations
verbs:
- get
- list
- watch
- apiGroups:
- ''
resources:
- namespaces
verbs:
- get
- list
- watch
state: present
name: "install ClusterRole {{ namespace }} to {{ namespace }} namespace"
- k8s:
definition:
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: "{{ namespace }}"
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: "{{ namespace }}"
subjects:
- kind: ServiceAccount
name: "{{ namespace }}-user"
namespace: "{{ namespace }}"
state: present
name: "install ClusterRoleBinding {{ namespace }} to {{ namespace }} namespace"
- shell: "kubectl -n {{ namespace }} -o yaml get sa {{ namespace }}-user"
register: raw
- name: load yaml
set_fact:
service_account: "{{ raw.stdout|from_yaml }}"
- name: "fetch {{ namespace }} secret"
shell: "kubectl -n {{ namespace }} get secret {{ service_account['secrets'][1]['name'] }} -o yaml"
register: raw
- name: "load yaml"
set_fact:
secret: "{{ raw.stdout|from_yaml }}"
- shell: kubectl get nodes -l node-role.kubernetes.io/master -o yaml
register: raw
- name: "load yaml"
set_fact:
k8s_master_nodes: "{{ raw.stdout|from_yaml }}"
- name: download template to ansible controller
get_url:
url: https://gist.githubusercontent.com/egeneralov/6c3aada224923e2bba42fca5559e0880/raw/cfcce27d124eb64fb16e18c213b6c25352c4074f/namespace.kubeconfig.yaml.j2
remote_src: yes
dest: /tmp/namespace.kubeconfig.yaml.j2
delegate_to: localhost
- name: template
template:
src: /tmp/namespace.kubeconfig.yaml.j2
dest: "{{ item }}"
with_items: "{{ output }}"
apiVersion: v1
kind: Config
preferences: {}
# Define the cluster
clusters:
- cluster:
certificate-authority-data: {{ secret['data']['ca.crt'] }}
# You'll need the API endpoint of your Cluster here:
server: https://{{ k8s_master_nodes['items'][0]['status']['addresses'][0]['address']|default('127.0.0.1') }}:6443
name: local
# Define the user
users:
- name: {{ namespace }}-user
user:
as-user-extra: {}
token: {{ secret['data']['token'] | b64decode }}
# Define the context: linking a user to a cluster
contexts:
- context:
cluster: local
namespace: {{ namespace }}
user: {{ namespace }}-user
name: {{ namespace }}
# Define current context
current-context: {{ namespace }}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment