Thursday, June 6, 2019

Kubernetes Helm



https://helm.sh/docs/
The templates/ directory is for template files. When Tiller evaluates a chart, it will send all of the files in the templates/ directory through the template rendering engine. Tiller then collects the results of those templates and sends them on to Kubernetes.
The values.yaml file is also important to templates. This file contains the default values for a chart. These values may be overridden by users during helm install or helm upgrade.


  • deployment.yaml: A basic manifest for creating a Kubernetes deployment
  • service.yaml: A basic manifest for creating a service endpoint for your deployment
  • _helpers.tpl: A place to put template helpers that you can re-use throughout the chart

In Kubernetes, a ConfigMap is simply a container for storing configuration data


$ helm install ./mychart

The helm get manifest command takes a release name (full-coral) and prints out all of the Kubernetes resources that were uploaded to the server. Each file begins with --- to indicate the start of a YAML document

  • Values: Values passed into the template from the values.yaml file and from user-supplied files. By default, Values is empty.
Chart: The contents of the Chart.yaml file. Any data in Chart.yaml will be accessible here. For example {{.Chart.Name}}-{{.Chart.Version}} will print out the mychart-0.1.0.
    • Files: This provides access to all non-special files in a chart. While you cannot use it to access templates, you can use it to access other files in the chart. See the section Accessing Files for more.
      • Files.Get is a function for getting a file by name (.Files.Get config.ini)
      • Files.GetBytes is a function for getting the contents of a file as an array of bytes instead of as a string. This is useful for things like images.

    Some teams, like the Helm Charts team, choose to use only initial lower case letters in order to distinguish local names from those built-in. I

    ts contents come from four sources:
    • The values.yaml file in the chart
    • If this is a subchart, the values.yaml file of a parent chart
    • A values file is passed into helm install or helm upgrade with the -f flag (helm install -f myvals.yaml ./mychart)
    • Individual parameters passed with --set (such as helm install --set foo=bar ./mychart)
    If you need to delete a key from the default values, you may override the value of the key to be null, in which case Helm will remove the key from the overridden values merge.

    helm install stable/drupal --set image=my-registry/drupal:0.1.0 --set livenessProbe.exec.command=[cat,docroot/CHANGELOG.txt] --set livenessProbe.httpGet=null

      drink: {{ quote .Values.favorite.drink }}
    


    Helm has over 60 available functions. Some of them are defined by the Go template language itself. Most of the others are part of the Sprig template library

    A pipeline is evaluated as false if the value is:
    • a boolean false
    • a numeric zero
    • an empty string
    • nil (empty or null)
    • an empty collection (mapslicetupledictarray)

      {{ if and .Values.favorite.drink (eq .Values.favorite.drink "coffee") }}mug: true{{ end }}

    When the template engine runs, it removes the contents inside of {{ and }}, but it leaves the remaining whitespace exactly as is.

    First, the curly brace syntax of template declarations can be modified with special characters to tell the template engine to chomp whitespace. {{- (with the dash and space added) indicates that whitespace should be chomped left, while -}} means whitespace to the right should be consumed. Be careful! Newlines are whitespace!
    Make sure there is a space between the - and the rest of your directive. {{- 3 }} means “trim left whitespace and print 3” while {{-3}} means “print -3”.
      {{- if eq .Values.favorite.drink "coffee"}}
      mug: true
      {{- end}}
    

    Finally, sometimes it’s easier to tell the template system how to indent for you instead of trying to master the spacing of template directives. For that reason, you may sometimes find it useful to use the indent function ({{indent 2 "mug:true"}}).


    . is a reference to the current scope. So .Values tells the template to find the Valuesobject in the current scope.

      {{- with .Values.favorite }}
      drink: {{ .drink | default "tea" | quote }}
      food: {{ .food | upper | quote }}
      {{- end }}
    

      toppings: |-
        {{- range .Values.pizzaToppings }}
        - {{ . | title | quote }}
        {{- end }}


    The toppings: |- line is declaring a multi-line string. So our list of toppings is actually not a YAML list. It’s a big string. Why would we do this? Because the data in ConfigMaps data is composed of key/value pairs, where both the key and the value are simple strings. To understand why this is the case, take a look at the Kubernetes ConfigMap docs. For us, though, this detail doesn’t matter much.
    The |- marker in YAML takes a multi-line string. This can be a useful technique for embedding big blocks of data inside of your manifests, as exemplified here

      sizes: |-
        {{- range tuple "small" "medium" "large" }}
        - {{ . }}
        {{- end }}
    

    a variable is a named reference to another object. It follows the form $name. Variables are assigned with a special assignment operator: := 

      {{- $relname := .Release.Name -}}
    

      toppings: |-
        {{- range $index, $topping := .Values.pizzaToppings }}
          {{ $index }}: {{ $topping }}
        {{- end }}
    


      {{- range $key, $val := .Values.favorite }}
      {{ $key }}: {{ $val | quote }}
      {{- end}}
    

    there is one variable that is always global - $ - this variable will always point to the root context. This can be very useful when you are looping in a range and need to know the chart’s release name.




      name: {{ .Release.Name }}-configmap
    

    The template directive {{ .Release.Name }} injects the release name into the template. The values that are passed into a template can be thought of as namespaced objects, where a dot (.) separates each namespaced element.
    The leading dot before Release indicates that we start with the top-most namespace for this scope (we’ll talk about scope in a bit). So we could read .Release.Name as “start at the top namespace, find the Release object, then look inside of it for an object called Name”.
    The Release object is one of the built-in objects for Helm

    You can run helm get manifest clunky-serval to see the entire generated YAML.



    • Use {{ .Files.Get "FILENAME" }} to get the contents of a file in the chart.
    • Use {{ include "TEMPLATE" . }} to render a template and then place its contents into the chart.


    For example, this template snippet includes a template called mytpl, then lowercases the result, then wraps that in double quotes.
    value: {{ include "mytpl" . | lower | quote }}
    The required function allows you to declare a particular values entry as required for template rendering. If the value is empty, the template rendering will fail with a user submitted error message.
    The following example of the required function declares an entry for .Values.who is required, and will print an error message when that entry is missing:
    value: {{ required "A valid .Values.who entry required!" .Values.who }}
    When using the include function, you can pass it a custom object tree built from the current context by using the dict function:
    {{- include "mytpl" (dict "key1" .Values.originalKey1 "key2" .Values.originalKey2) }}
    The tpl function allows developers to evaluate strings as templates inside a template. This is useful to pass a template string as a value to a chart or render external configuration files. Syntax: {{ tpl TEMPLATE_STRING VALUES }}

    {{ tpl (.Files.Get "conf/app.conf") . }}
    
    drink: {{ .Values.favorite.drink | default "tea" | quote }}
    Operators are implemented as functions that return a boolean value. To use eqneltgtandornot etcetera place the operator at the front of the statement followed by its parameters just as you would a function. To chain multiple operations together, separate individual functions by surrounding them with parentheses.
    {{/* include the body of this if statement when the variable .Values.fooString exists and is set to "foo" */}}
    {{ if and .Values.fooString (eq .Values.fooString "foo") }}
        {{ ... }}
    {{ end }}
    
    
    {{/* do not include the body of this if statement because unset variables evaluate to false and .Values.setVariable was negated with the not function. */}}
    {{ if or .Values.anUnsetVariable (not .Values.aSetVariable) }}
       {{ ... }}
    {{ end }}


    https://github.com/helm/helm/blob/master/docs/chart_best_practices/templates.md
    Blocks (such as control structures) may be indented to indicate flow of the template code.
    {{ if $foo -}}
      {{- with .Bar }}Hello{{ end -}}
    {{- end -}} 
    

    https://learnxinyminutes.com/docs/yaml/

    It’s a strict superset of JSON, with the addition of syntactically significant newlines and indentation, like Python. Unlike Python, however, YAML doesn’t allow literal tab characters for indentation.

    # Multiple-line strings can be written either as a 'literal block' (using |),
    # or a 'folded block' (using '>').
    


    https://learnxinyminutes.com/docs/yaml/

    https://stackoverflow.com/questions/3790454/in-yaml-how-do-i-break-a-string-over-multiple-lines

    Block scalar styles (>|)

    These allow escaping, and add a new line (\n) to the end of your string.
    > Folded style may be what you want:
    Key: >
      this is my very very very
      long string
    
    → this is my very very very long string\n
    If you use the | literal style method, a newline character is inserted into the string at each end of line:
    Key: |
      this is my very very very 
      long string
    
    → this is my very very very\nlong string\n
    Here's the official definition from the YAML Spec 1.2

    Scalar content can be written in block notation, using a literal style (indicated by “|”) where all line breaks are significant. Alternatively, they can be written with the folded style (denoted by “>”) where each line break is folded to a space unless it ends an empty or a more-indented line.

    Block styles with block chomping indicator (>-|->+|+)

    You can control the handling of the final new line in the string, and any trailing blank lines (\n\n) by adding a block chomping indicator character:
    • >|: "clip": keep the line feed, remove the trailing blank lines.
    • >-|-: "strip": remove the line feed, remove the trailing blank lines.
    • >+|+: "keep": keep the line feed, keep trailing blank lines.

    https://symfony.com/doc/current/components/yaml/yaml_format.html
    Sequences use a dash followed by a space:
    1
    2
    3

    - PHP
    - Perl
    - Python

    Mappings use a colon followed by a space (: ) to mark each key/value pair:
    1
    2
    3

    PHP: 5.2
    MySQL: 5.1
    Apache: 2.2.20

    YAML uses indentation with one or more spaces to describe nested collections:
    1
    2
    3
    4
    5
    6

    'symfony 1.0':
      PHP:    5.0
      Propel: 1.2
    'symfony 1.2':
      PHP:    5.2
      Propel: 1.3

    https://banzaicloud.com/blog/creating-helm-charts/
    “Helm helps you manage Kubernetes applications — Helm Charts helps you define, install, and upgrade even the most complex Kubernetes application.” - https://helm.sh/
    Helm’s operation is based on cooperation between two main components: a command line tool called helm, and a server component called tiller, which has to run on the cluster it manages.

    $ brew install kubernetes-helm
    


    To start deploying applications to a pure Kubernetes cluster you have to install tiller with the helm init command of the CLI tool.
    # Select the Kubernetes context you want to use
    $ kubectl config use-context docker-for-desktop
    $ helm init

    Last but not least, debug. To understand what will happen after Helm renders templates we can use the --debug and --dry-run options.
    $ helm install chart-name --debug --dry-run

    What did I install?

    Getting values used by a running deployment may also come in handy.
    $ helm get values release-name


    Edit: I was running helm template in the wrong place. To demonstrate that it works ok on a properly structured directory, use helm create foo; helm template foo. Helm is just not forgiving nor communicative about directories not structured exactly how it expects.

    Labels

    Review (572) System Design (334) System Design - Review (198) Java (189) Coding (75) Interview-System Design (65) Interview (63) Book Notes (59) Coding - Review (59) to-do (45) Linux (43) Knowledge (39) Interview-Java (35) Knowledge - Review (32) Database (31) Design Patterns (31) Big Data (29) Product Architecture (28) MultiThread (27) Soft Skills (27) Concurrency (26) Cracking Code Interview (26) Miscs (25) Distributed (24) OOD Design (24) Google (23) Career (22) Interview - Review (21) Java - Code (21) Operating System (21) Interview Q&A (20) System Design - Practice (20) Tips (19) Algorithm (17) Company - Facebook (17) Security (17) How to Ace Interview (16) Brain Teaser (14) Linux - Shell (14) Redis (14) Testing (14) Tools (14) Code Quality (13) Search (13) Spark (13) Spring (13) Company - LinkedIn (12) How to (12) Interview-Database (12) Interview-Operating System (12) Solr (12) Architecture Principles (11) Resource (10) Amazon (9) Cache (9) Git (9) Interview - MultiThread (9) Scalability (9) Trouble Shooting (9) Web Dev (9) Architecture Model (8) Better Programmer (8) Cassandra (8) Company - Uber (8) Java67 (8) Math (8) OO Design principles (8) SOLID (8) Design (7) Interview Corner (7) JVM (7) Java Basics (7) Kafka (7) Mac (7) Machine Learning (7) NoSQL (7) C++ (6) Chrome (6) File System (6) Highscalability (6) How to Better (6) Network (6) Restful (6) CareerCup (5) Code Review (5) Hash (5) How to Interview (5) JDK Source Code (5) JavaScript (5) Leetcode (5) Must Known (5) Python (5)

    Popular Posts