|
| 1 | +# Components |
| 2 | + |
| 3 | +## Contents |
| 4 | + |
| 5 | +- [Components](#components) |
| 6 | + - [Introduction](#introduction) |
| 7 | + - [Recommender](#recommender) |
| 8 | + - [Running](#running-the-recommender) |
| 9 | + - [Implementation](#implementation-of-the-recommender) |
| 10 | + - [Updater](#updater) |
| 11 | + - [Current implementation](#current-implementation) |
| 12 | + - [Missing Parts](#missing-parts) |
| 13 | + - [Admission Controller](#admission-controller) |
| 14 | + - [Running](#running-the-admission-controller) |
| 15 | + - [Implementation](#implementation-of-the-admission-controller) |
| 16 | + |
| 17 | +## Introduction |
| 18 | + |
| 19 | +The VPA project consists of 3 components: |
| 20 | + |
| 21 | +- [Recommender](#recommender) - monitors the current and past resource consumption and, based on it, |
| 22 | + provides recommended values for the containers' cpu and memory requests. |
| 23 | + |
| 24 | +- [Updater](#updater) - checks which of the managed pods have correct resources set and, if not, |
| 25 | + kills them so that they can be recreated by their controllers with the updated requests. |
| 26 | + |
| 27 | +- [Admission Controller](#admission-controller) - sets the correct resource requests on new pods (either just created |
| 28 | + or recreated by their controller due to Updater's activity). |
| 29 | + |
| 30 | +More on the architecture can be found [HERE](https://github.com/kubernetes/design-proposals-archive/blob/main/autoscaling/vertical-pod-autoscaler.md). |
| 31 | + |
| 32 | +## Recommender |
| 33 | + |
| 34 | +Recommender is the core binary of Vertical Pod Autoscaler system. |
| 35 | +It computes the recommended resource requests for pods based on |
| 36 | +historical and current usage of the resources. |
| 37 | +The current recommendations are put in status of the VPA resource, where they |
| 38 | +can be inspected. |
| 39 | + |
| 40 | +## Running the recommender |
| 41 | + |
| 42 | +- In order to have historical data pulled in by the recommender, install |
| 43 | + Prometheus in your cluster and pass its address through a flag. |
| 44 | +- Create RBAC configuration from `../deploy/vpa-rbac.yaml`. |
| 45 | +- Create a deployment with the recommender pod from |
| 46 | + `../deploy/recommender-deployment.yaml`. |
| 47 | +- The recommender will start running and pushing its recommendations to VPA |
| 48 | + object statuses. |
| 49 | + |
| 50 | +### Implementation of the recommender |
| 51 | + |
| 52 | +The recommender is based on a model of the cluster that it builds in its memory. |
| 53 | +The model contains Kubernetes resources: *Pods*, *VerticalPodAutoscalers*, with |
| 54 | +their configuration (e.g. labels) as well as other information, e.g. usage data for |
| 55 | +each container. |
| 56 | + |
| 57 | +After starting the binary, recommender reads the history of running pods and |
| 58 | +their usage from Prometheus into the model. |
| 59 | +It then runs in a loop and at each step performs the following actions: |
| 60 | + |
| 61 | +- update model with recent information on resources (using listers based on |
| 62 | + watch), |
| 63 | +- update model with fresh usage samples from Metrics API, |
| 64 | +- compute new recommendation for each VPA, |
| 65 | +- put any changed recommendations into the VPA resources. |
| 66 | + |
| 67 | +## Updater |
| 68 | + |
| 69 | +Updater component for Vertical Pod Autoscaler described in the [Vertical Pod Autoscaler - design proposal](https://github.com/kubernetes/community/pull/338) |
| 70 | + |
| 71 | +Updater runs in Kubernetes cluster and decides which pods should be restarted |
| 72 | +based on resources allocation recommendation calculated by Recommender. |
| 73 | +If a pod should be updated, Updater will try to evict the pod. |
| 74 | +It respects the pod disruption budget, by using Eviction API to evict pods. |
| 75 | +Updater does not perform the actual resources update, but relies on Vertical Pod Autoscaler admission plugin |
| 76 | +to update pod resources when the pod is recreated after eviction. |
| 77 | + |
| 78 | +### Current implementation |
| 79 | + |
| 80 | +Runs in a loop. On one iteration performs: |
| 81 | + |
| 82 | +- Fetching Vertical Pod Autoscaler configuration using a lister implementation. |
| 83 | +- Fetching live pods information with their current resource allocation. |
| 84 | +- For each replicated pods group calculating if pod update is required and how many replicas can be evicted. |
| 85 | +Updater will always allow eviction of at least one pod in replica set. Maximum ratio of evicted replicas is specified by flag. |
| 86 | +- Evicting pods if recommended resources significantly vary from the actual resources allocation. |
| 87 | +Threshold for evicting pods is specified by recommended min/max values from VPA resource. |
| 88 | +Priority of evictions within a set of replicated pods is proportional to sum of percentages of changes in resources |
| 89 | +(i.e. pod with 15% memory increase 15% cpu decrease recommended will be evicted |
| 90 | +before pod with 20% memory increase and no change in cpu). |
| 91 | + |
| 92 | +### Missing parts |
| 93 | + |
| 94 | +- Recommendation API for fetching data from Vertical Pod Autoscaler Recommender. |
| 95 | + |
| 96 | +## Admission-controller |
| 97 | + |
| 98 | +This is a binary that registers itself as a Mutating Admission Webhook |
| 99 | +and because of that is on the path of creating all pods. |
| 100 | +For each pod creation, it will get a request from the apiserver and it will |
| 101 | +either decide there's no matching VPA configuration or find the corresponding |
| 102 | +one and use current recommendation to set resource requests in the pod. |
| 103 | + |
| 104 | +### Running the admission-controller |
| 105 | + |
| 106 | +1. You should make sure your API server supports Mutating Webhooks. |
| 107 | +Its `--admission-control` flag should have `MutatingAdmissionWebhook` as one of |
| 108 | +the values on the list and its `--runtime-config` flag should include |
| 109 | +`admissionregistration.k8s.io/v1beta1=true`. |
| 110 | +To change those flags, ssh to your API Server instance, edit |
| 111 | +`/etc/kubernetes/manifests/kube-apiserver.manifest` and restart kubelet to pick |
| 112 | +up the changes: ```sudo systemctl restart kubelet.service``` |
| 113 | +1. Generate certs by running `bash gencerts.sh`. This will use kubectl to create |
| 114 | + a secret in your cluster with the certs. |
| 115 | +1. Create RBAC configuration for the admission controller pod by running |
| 116 | + `kubectl create -f ../deploy/admission-controller-rbac.yaml` |
| 117 | +1. Create the pod: |
| 118 | + `kubectl create -f ../deploy/admission-controller-deployment.yaml`. |
| 119 | + The first thing this will do is it will register itself with the apiserver as |
| 120 | + Webhook Admission Controller and start changing resource requirements |
| 121 | + for pods on their creation & updates. |
| 122 | +1. You can specify a path for it to register as a part of the installation process |
| 123 | + by setting `--register-by-url=true` and passing `--webhook-address` and `--webhook-port`. |
| 124 | +1. You can specify a minimum TLS version with `--min-tls-version` with acceptable values being `tls1_2` (default), or `tls1_3`. |
| 125 | +1. You can also specify a comma or colon separated list of ciphers for the server to use with `--tls-ciphers` if `--min-tls-version` is set to `tls1_2`. |
| 126 | +1. You can specify a comma separated list to set webhook labels with `--webhook-labels`, example format: key1:value1,key2:value2. |
| 127 | + |
| 128 | +### Implementation of the Admission Controller |
| 129 | + |
| 130 | +All VPA configurations in the cluster are watched with a lister. |
| 131 | +In the context of pod creation, there is an incoming https request from |
| 132 | +apiserver. |
| 133 | +The logic to serve that request involves finding the appropriate VPA, retrieving |
| 134 | +current recommendation from it and encodes the recommendation as a json patch to |
| 135 | +the Pod resource. |
0 commit comments