Git Product home page Git Product logo

landscaper's Introduction

Landscaper is no more

Thanks for your interest in Landscaper. It was conceived in a turbulent time where k8s was relatively new, and Helm was brand new. Multiple people had the same ideas and vision as we (our team at Eneco Energy Trade) had, which now even has a name: GitOps. This project was cool as long as it lasted, but it never gained much traction. Other projects similar to Landscaper emerged, and have become more popular. Better go there, since there is no active community supporting this project. The most popular alternative to Landscaper seems to be https://github.com/roboll/helmfile.

Landscaper

Build Status Go Report Card Go Doc Say Thanks!

Landscaper takes a set of Helm Chart references with values (a desired state), and realizes this in a Kubernetes cluster. The intended use case is to have this desired state under version control, and let Landscaper first test and then apply the state as part of the CI/CD stages.

The Landscaper project is an ongoing project in an early stage, opened due to demand in the community. Contributions and feedback are more than welcome!

Introduction

Why

  • The set of applications in the Kubernetes cluster is potentially large and complex;
  • Manually inspecting and administering them, and keeping different environments (e.g. production, acceptance) in sync is laborious and difficult;
  • Cooperating with multiple tenants in this shared cluster increases the complexity.

How

  • Have a blue print of what the landscape (apps in the cluster) looks like;
  • Keep track of changes: when, what, why and by who;
  • Allow others to review changes before applying them;
  • Let the changes be promoted to specific environments.

What

  • A Git repository contains a desired state description of the landscape, with CI/CD and a review before merge regime;
  • Landscaper, an app that eliminates difference between desired and actual state of Helm releases in a Kubernetes cluster.

Installation

Binaries are available here; Docker images here. On macOS using Homebrew, a brew install landscaper should do.

From source

You must have a working Go environment with dep and GNU Make installed.

From a terminal:

  cd $GOPATH
  mkdir -p src/github.com/eneco/
  cd !$
  git clone https://github.com/Eneco/landscaper.git
  cd landscaper
  make bootstrap build

Outputs the landscaper binary in ./build/landscaper.

Usage

Landscaper consists of a core API and a command line interface (CLI) that consumes this API. It takes as input a set of files that constitute the desired state. The CLI assumes that kubectl and helm have been setup!

These files contain (a) reference(s) to a Helm Chart and its configuration (Values). Additionally, Landscaper receives settings (tokens, credentials) needed to query and modify a Kubernetes cluster via Helm/Tiller. Typically these settings are provided by the CI/CD system.

The CLI uses a command structure in the spirit of git et al. The main command is landscaper apply to apply a desired state. The apply command accepts the following arguments:

Usage:
  landscaper apply [files]... [flags]

Flags:
      --azure-keyvault string         azure keyvault for fetching secrets. Azure credentials must be provided in the environment.
      --chart-dir string              (deprecated; use --helm-home) Helm home directory (default "$HOME/.helm")
      --config-override-file string   global configuration overrides. component specific environment overrides take precedence over this.
      --context string                the kube context to use. defaults to the current context
      --dir string                    (deprecated) path to a folder that contains all the landscape desired state files; overrides LANDSCAPE_DIR
      --disable stringSlice           Stages to be disabled. Available stages are create/update/delete.
      --dry-run                       simulate the applying of the landscape. useful in merge requests
      --helm-home string              Helm home directory (default "$HOME/.helm")
      --env string                    environment specifier. selects value overrides by environment.
      --loop                          keep landscape in sync forever
      --loop-interval duration        when running in a loop the interval between invocations (default 5m0s)
      --namespace string              namespace to apply the landscape to; overrides LANDSCAPE_NAMESPACE (default "default")
      --no-prefix                     disable prefixing release names
      --prefix string                 prefix release names with this string instead of <namespace>; overrides LANDSCAPE_PREFIX
      --tiller-namespace string       Tiller namespace for Helm (default "kube-system")
  -v, --verbose                       be verbose
      --wait                          wait for all resources to be ready
      --wait-timeout duration         interval to wait for all resources to be ready (default 5m0s)

Instead of using arguments, environment variables can be used. When arguments are present, they override environment variables. --namespace is used to isolate landscapes through Kubernetes namespaces. Unless otherwise specified, Helm releases are prefixed with the same namespace string to avoid collisions, since Helm release names aren't namespaced. As of version 1.0.3, components can specify their namespace. This will override any provided global namespace.

Landscaper can also be run as a control loop that constantly watches the desired landscape and applies it to the cluster. With this you can deploy landscaper once in your cluster, pass it a reference to a landscape description and have Landscaper apply it whenever the landscape changes.

Connection to Tiller is made by setting up a port-forward to it's pod. However, when $HELM_HOST is defined with a "host:port" in it, a direct connection is made to that host and port instead.

Azure Credentials

When using the --azure-keyvault argument, Azure Service Principal credentials must be available in the environment:

  • AZURE_CLIENT_ID
  • AZURE_CLIENT_SECRET
  • AZURE_TENANT_ID

The key vault DNS suffix defaults to the public cloud, vault.azure.net, but can be overridden with AZURE_KEYVAULT_DNS_SUFFIX.

Desired State Files

Input desired state files are in YAML and contain the name that identifies the "component", a reference to a chart, configuration and optionally secrets.

name: my-component
release:
	chart: "example/chart:0.1.0"
	version: 0.1.0

# This will become the .Values override for the chart deployment.
configuration: 
  hostname: "example"
  url: "http://default.example.com"
  
# These configurations can be selected with the '--env' flag 
# and will override the above values. 
environments: 
  dev:
    url: "http://dev.example.com"
  prod:
    url: "http://prod.example.com"

# These secrets will be fetched, and instantiated as a Kubernetes 
# secret whose name will be written to .Values.secretsRef
secrets:     
- my-secret
- my-other-secret

Installing the above component with default prefix and --env dev will result in chart value overrides

hostname: "example"
url: "http://dev.example.com"
secretsRef: 'default-my-component'

and a Kubernetes secret named default-my-component with the contents:

Secrets

Secrets can be provided as a list or as a map. If a list is provided then the same string is used for the key in the Kubernetes secret and to find the secret value.

...
secrets:
	- my-secret
	- my-other-secret

is realised as:

    my-secret: <value of MY_SECRET environment variable>
    my-other-secret: <value MY_OTHER_SECRET environment variable>

If a map is provided the key is the used as the Kubernetes secret key, and the value is used to fetch the secret value.

...
secrets:
	secret1: my-secret
	secret2: my-other-secret

is realised as:

    secret1: <value of MY_SECRET environment variable>
    secret2: <value MY_OTHER_SECRET environment variable>

By default the secrets are read from the environment with the string converted to UPPER_SNAKE_CASE e.g. export MY_SECRET=Rumpelstiltskin

Global configuration override file

You can specify a global configuration override file with the --config-override-file argument. This will override chart and component defaults, but not environment specific configuration.

# my-component.yaml
name: my-component
release:
  chart: "example/chart:0.1.0"
  version: 0.1.0

# This will become the .Values override for the chart deployment.
configuration:
  hostname: "example"
  url: "http://default.example.com"
environments:
  env1:
    hostname: "env1"



# global.yaml
hostname: "global"
url: "http://global.example.com"

Installing the above component with --config-override-file global.yaml and --env env1 will result in chart value overrides

hostname: "env1"
url: "http://global.example.com"

Secret Usage in Helm Charts

Secrets are made available as Kubernetes Secrets (as shown above). The helm chart needs to be setup to use the secret in a pod, where the secret name is made available by the landscaper as .Values.secretsRef. For example, as an environment variable:

env:
- name: MY_SECRET
  valueFrom:
    secretKeyRef:
      name: {{ .Values.secretsRef }}
      key: my-secret

Or mounted volume:

volumes:
- name: my-secret
  secret:
    secretName: {{ .Values.secretsRef }}
    items:
    - key: my-secret
      path: secrets/my-secret
      mode: 511

Example

An example is provided here.

Example Use Case

We, at Eneco, have setup a git repository with the inputs to the landscaper. During CI, non-master branches are Landscaped --dry-run to validate the inputs. After a pull request is reviewed, the changes are merged into master after which the Landscaper applies the new desired state.

Example disable a stage

Landscaper is build on philosphy of applying charts in three stages delete, update and create and in that order.

However it allows to disable stages during apply. So users can cover their corner cases.

e.g to disable delete stage

landscaper apply [files] --disable delete

and to disable delete and update

landscaper apply [files] --disable delete --disable update

Compatibility

Landscaper uses both Helm and Kubernetes. The following Landscaper releases are built against the following versions:

Landscaper Helm Kubernetes
1.0.24 2.13.1 1.12.5
1.0.23 2.13.1 1.12.5
1.0.21 2.11.0 1.11.1
1.0.20 2.11.0 1.11.1
1.0.19 2.10.0 1.10.3
1.0.17 2.8.2 1.9
1.0.16 2.7.2 1.8
1.0.15 2.7.2 1.8
1.0.14 2.7.2 1.8
1.0.13 2.7.2 1.8
1.0.12 2.7.2 1.8
1.0.11 2.6.1 1.7
1.0.10 2.5.1 1.6
1.0.9 2.5.1 1.6
1.0.8 2.4.2 1.6
1.0.7 2.4.2 1.6
1.0.6 2.4.2 1.6
1.0.5 2.4.2 1.6
1.0.4 2.3.1 1.5
1.0.3 2.1.3 1.5
1.0.2 2.1.3 1.5
1.0.1 2.1.3 1.5
1.0.0 2.1.3 1.5

Contributing

We'd love to accept your contributions! Please use GitHub pull requests: fork the repo, develop and test your code, semantically commit (as of April 2017) and submit a pull request. Thanks!

landscaper's People

Contributors

adriaanmutter avatar atopuzovic-dw avatar carlosjgp avatar chenrui333 avatar fsero avatar johnhofman avatar kragniz avatar linki avatar mbaan avatar otaviof avatar philipbjorge avatar rollulus avatar royjs avatar tg90nor avatar tommyminds avatar zmalik avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

landscaper's Issues

Colorize the diff output

It would be great to colorize the diff output, so removed lines are red and added lines are green.

Fix log timestamp prefix

Either logrus or "github.com/x-cray/logrus-prefixed-formatter" changed something in a non-backward manner.

landscaper update does not update pods of ReplicaControllers or DaemonSets

landscaper update does not update pods of ReplicaControllers or DaemonSets.

Ran into this while updating environment variables in a daemonset.

It looks like this is supported by helm with the --recreate-pods argument which is a temporary workaround in place until kubernetes upstream handles it.

It seems like this option would best be supported in the landscape definition?
I'm thinking, I only want to use this argument on specific, impacted charts (e.g. logspout) especially since it does not do a soft restart right now -- helm/helm#1702


A workaround today is to build in hooks to the chart to handle recreating it's pods.

helm/helm#1648


Thoughts on a plan of action?

Specify a namespace to deploy chart in landscape definition

It'd be nice if you could specify which namespace to deploy charts into in a landscape definition file. Something like:

name: thing
release:
  chart: repo/thing:0.1.4
  version: 0.1.1
  namespace: doot-system
configuration:
  something: doot

Namespace information ignored in current context

Since landscaper (and helm) make use of ~/.kube/config and really on current context to work. it's strange that landscaper does not use namespace defined in that context. Atm. the default namespace is called "default" regardless of the namespace specified in the current context.

running apply on a file without changes results in diff and helm update

Expected: Running landscaper apply on the same file multiple times should not result in more tiller/helm versions.
Actual: Each run detects a 'diff' when it really isn't and adds to helm/tiller versions.

Simple landscaper yaml

$ cat test/redis.yaml 
name: redis
release:
  chart: stable/redis
  version: 0.5.2

Initial install

$ landscaper apply test/redis.yaml  --namespace testing
[0000]  INFO  This is Landscaper v1.0.4 commit=74e77ff2b221feda63c0c4435a10812979f11ed0 tag=1.0.4
[0000]  INFO  Apply landscape desired state chartDir=/home/kyle/.helm dir= dryRun=false namespace=testing releasePrefix=testing- verbose=false
[0000]  INFO  Obtain desired state from files files=[test/redis.yaml]
[0000]  INFO  Obtain current state Helm Releases (Components) from Tiller
[0001]  INFO  Connected to Tiller clientServerCompatible=true tillerVersion=v2.3.1
[0001]  INFO  Retrieved Releases (Components) landscapedComponents=0 totalReleases=0
[0001]  INFO  Apply desired state create=1 delete=0 update=0
[0001]  INFO  Create: testing-redis
[0001]  INFO  Diff:
--- Current <none>
+++ Desired testing-redis
@@ -0,0 +1,29 @@
+{
+  "name": "testing-redis",
+  "namespace": "testing",
+  "release": {
+    "chart": "redis",
+    "version": "0.5.2"
+  },
+  "configuration": {
+    "Name": "redis",
+    "_landscaper_metadata": {
+      "chartrepository": "stable",
+      "releaseversion": "0.5.2"
+    },
+    "image": "bitnami/redis:3.2.8-r3",
+    "imagePullPolicy": "IfNotPresent",
+    "persistence": {
+      "accessMode": "ReadWriteOnce",
+      "enabled": true,
+      "size": "8Gi"
+    },
+    "resources": {
+      "requests": {
+        "cpu": "100m",
+        "memory": "256Mi"
+      }
+    }
+  },
+  "secrets": []
+}

[0002]  INFO  Applied desired state sucessfully created=1 deleted=0 updated=0

Running again.

$ landscaper apply test/redis.yaml  --namespace testing
[0000]  INFO  This is Landscaper v1.0.4 commit=74e77ff2b221feda63c0c4435a10812979f11ed0 tag=1.0.4
[0000]  INFO  Apply landscape desired state chartDir=/home/kyle/.helm dir= dryRun=false namespace=testing releasePrefix=testing- verbose=false
[0000]  INFO  Obtain desired state from files files=[test/redis.yaml]
[0000]  INFO  Obtain current state Helm Releases (Components) from Tiller
[0000]  INFO  Connected to Tiller clientServerCompatible=true tillerVersion=v2.3.1
[0001]  INFO  Connected to Kubernetes kubernetesVersion=v1.6.2
[0001]  INFO  Retrieved Releases (Components) landscapedComponents=1 totalReleases=1
[0001]  INFO  testing-redis differs in namespace; don't update but delete + create instead
[0001]  INFO  Apply desired state create=0 delete=0 update=1
[0001]  INFO  Update: testing-redis
[0001]  INFO  Diff:
--- Current testing-redis
+++ Desired testing-redis
@@ -2,7 +2,7 @@
   "name": "testing-redis",
   "namespace": "testing",
   "release": {
-    "chart": "redis:0.5.2",
+    "chart": "redis",
     "version": "0.5.2"
   },
   "configuration": {

[0001]  INFO  Deleting existing secrets for component component=testing-redis namespace=testing
[0001]  INFO  No secrets found for component component=testing-redis namespace=testing
[0002]  INFO  Applied desired state sucessfully created=0 deleted=0 updated=1

With -v

$ landscaper apply test/redis.yaml  --namespace testing -v
[0000]  INFO  This is Landscaper v1.0.4 commit=74e77ff2b221feda63c0c4435a10812979f11ed0 tag=1.0.4
[0000]  INFO  Apply landscape desired state chartDir=/home/kyle/.helm dir= dryRun=false namespace=testing releasePrefix=testing- verbose=true
[0000]  INFO  Obtain desired state from files files=[test/redis.yaml]
[0000] DEBUG  Read desired state from file file=test/redis.yaml
[0000] DEBUG  coalesceComponent chart=redis
[0000] DEBUG  Load Chart chartRef=stable/redis
[0000] DEBUG  locateChartPath chartRef=stable/redis homePath=/home/kyle/.helm name=stable/redis version=
[0000] DEBUG  Look for cached local package chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz
[0000] DEBUG  Loaded Chart successfully chartRef=stable/redis
[0000] DEBUG  desired landscaper.Component{Name:"testing-redis", Namespace:"testing", Release:(*landscaper.Release)(0xc4203e14a0), Configuration:landscaper.Configuration{"Name":"redis", "_landscaper_metadata":map[string]interface {}{"chartrepository":"stable", "releaseversion":"0.5.2"}, "imagePullPolicy":"IfNotPresent", "persistence":map[string]interface {}{"enabled":true, "size":"8Gi", "accessMode":"ReadWriteOnce"}, "resources":map[string]interface {}{"requests":map[string]interface {}{"cpu":"100m", "memory":"256Mi"}}, "image":"bitnami/redis:3.2.8-r3"}, Secrets:landscaper.Secrets{}, SecretValues:landscaper.SecretValues{}}
[0000] DEBUG  Desired state has been read components=1 directory=
[0000]  INFO  Obtain current state Helm Releases (Components) from Tiller
[0000] DEBUG  listHelmReleases
[0000] DEBUG  Setup Helm Client helmClientVersion=v2.3.1
[0000] DEBUG  Create tiller tunnel tillerNamespace=kube-system
[0000] DEBUG  Created tiller tunnel port=39116
[0000]  INFO  Connected to Tiller clientServerCompatible=true tillerVersion=v2.3.1
[0001] DEBUG  Reading secrets for component component=testing-redis namespace=testing
[0001] DEBUG  Setup Kubernetes Client
[0001]  INFO  Connected to Kubernetes kubernetesVersion=v1.6.2
[0001] DEBUG  No secrets found for component component=testing-redis namespace=testing
[0001]  INFO  Retrieved Releases (Components) landscapedComponents=1 totalReleases=1
[0001]  INFO  testing-redis differs in namespace; don't update but delete + create instead
[0001]  INFO  Apply desired state create=0 delete=0 update=1
[0001]  INFO  Update: testing-redis
[0001]  INFO  Diff:
--- Current testing-redis
+++ Desired testing-redis
@@ -2,7 +2,7 @@
   "name": "testing-redis",
   "namespace": "testing",
   "release": {
-    "chart": "redis:0.5.2",
+    "chart": "redis",
     "version": "0.5.2"
   },
   "configuration": {

[0001] DEBUG  Load Chart chartRef=stable/redis
[0001] DEBUG  locateChartPath chartRef=stable/redis homePath=/home/kyle/.helm name=stable/redis version=
[0001] DEBUG  Look for cached local package chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz
[0001] DEBUG  Loaded Chart successfully chartRef=stable/redis
[0001]  INFO  Deleting existing secrets for component component=testing-redis namespace=testing
[0001]  INFO  No secrets found for component component=testing-redis namespace=testing
[0001] DEBUG  Update component chart=redis chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz dryrun=false release=testing-redis values=map[image:bitnami/redis:3.2.8-r3 Name:redis _landscaper_metadata:map[chartrepository:stable releaseversion:0.5.2] imagePullPolicy:IfNotPresent persistence:map[accessMode:ReadWriteOnce enabled:true size:8Gi] resources:map[requests:map[cpu:100m memory:256Mi]]]
[0002]  INFO  Applied desired state sucessfully created=0 deleted=0 updated=1

And kubectl goodness of the configmaps for tiller

$ kubectl -n kube-system get configmaps | grep testing-
testing-redis.v1                         1         6m
testing-redis.v2                         1         6m
testing-redis.v3                         1         3m

If chart version doesn't exist landscaper just uses a version from cache

Expected: Error saying chart doesn't exist (maybe a helm repo update could be run).
Actual: Just uses the latest one from helm cache ignoring the version

Also, if there did exist that version, but I hadn't updated my helm repo it would just silently use the one that I had as the chartPath instead of error/warning.

$ cat test/redis.yaml 
name: redis
release:
  chart: stable/redis
  version: 5.5.5 # doesn't exist
$ landscaper apply test/redis.yaml  --namespace testing2 -v --dry-run
[0000]  INFO  This is Landscaper v1.0.4 commit=74e77ff2b221feda63c0c4435a10812979f11ed0 tag=1.0.4
[0000]  INFO  Apply landscape desired state chartDir=/home/kyle/.helm dir= dryRun=true namespace=testing2 releasePrefix=testing2- verbose=true
[0000]  INFO  Obtain desired state from files files=[test/redis.yaml]
[0000] DEBUG  Read desired state from file file=test/redis.yaml
[0000] DEBUG  coalesceComponent chart=redis
[0000] DEBUG  Load Chart chartRef=stable/redis
[0000] DEBUG  locateChartPath chartRef=stable/redis homePath=/home/kyle/.helm name=stable/redis version=
[0000] DEBUG  Look for cached local package chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz
[0000] DEBUG  Loaded Chart successfully chartRef=stable/redis
[0000] DEBUG  desired landscaper.Component{Name:"testing2-redis", Namespace:"testing2", Release:(*landscaper.Release)(0xc420398b60), Configuration:landscaper.Configuration{"image":"bitnami/redis:3.2.8-r3", "imagePullPolicy":"IfNotPresent", "persistence":map[string]interface {}{"accessMode":"ReadWriteOnce", "enabled":true, "size":"8Gi"}, "resources":map[string]interface {}{"requests":map[string]interface {}{"cpu":"100m", "memory":"256Mi"}}, "Name":"redis", "_landscaper_metadata":map[string]interface {}{"chartrepository":"stable", "releaseversion":"5.5.5"}}, Secrets:landscaper.Secrets{}, SecretValues:landscaper.SecretValues{}}
[0000] DEBUG  Desired state has been read components=1 directory=
[0000]  INFO  Obtain current state Helm Releases (Components) from Tiller
[0000] DEBUG  listHelmReleases
[0000] DEBUG  Setup Helm Client helmClientVersion=v2.3.1
[0000] DEBUG  Create tiller tunnel tillerNamespace=kube-system
[0000] DEBUG  Created tiller tunnel port=38350
[0000]  INFO  Connected to Tiller clientServerCompatible=true tillerVersion=v2.3.1
[0001]  INFO  Retrieved Releases (Components) landscapedComponents=0 totalReleases=0
[0001]  INFO  Apply desired state create=1 delete=0 update=0
[0001]  INFO  Create: testing2-redis
[0001]  INFO  Diff:
--- Current <none>
+++ Desired testing2-redis
@@ -0,0 +1,29 @@
+{
+  "name": "testing2-redis",
+  "namespace": "testing2",
+  "release": {
+    "chart": "redis",
+    "version": "5.5.5"
+  },
+  "configuration": {
+    "Name": "redis",
+    "_landscaper_metadata": {
+      "chartrepository": "stable",
+      "releaseversion": "5.5.5"
+    },
+    "image": "bitnami/redis:3.2.8-r3",
+    "imagePullPolicy": "IfNotPresent",
+    "persistence": {
+      "accessMode": "ReadWriteOnce",
+      "enabled": true,
+      "size": "8Gi"
+    },
+    "resources": {
+      "requests": {
+        "cpu": "100m",
+        "memory": "256Mi"
+      }
+    }
+  },
+  "secrets": []
+}

[0001] DEBUG  Load Chart chartRef=stable/redis
[0001] DEBUG  locateChartPath chartRef=stable/redis homePath=/home/kyle/.helm name=stable/redis version=
[0001] DEBUG  Look for cached local package chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz
[0001] DEBUG  Loaded Chart successfully chartRef=stable/redis
[0001] DEBUG  Create component chart=redis chartPath=/tmp/landscaper/stable/redis-0.5.2.tgz dryrun=true rawValues=_landscaper_metadata:
  chartrepository: stable
  releaseversion: 5.5.5
Name: redis
image: bitnami/redis:3.2.8-r3
imagePullPolicy: IfNotPresent
persistence:
  accessMode: ReadWriteOnce
  enabled: true
  size: 8Gi
resources:
  requests:
    cpu: 100m
    memory: 256Mi
 release=testing2-redis values=map[imagePullPolicy:IfNotPresent persistence:map[enabled:true size:8Gi accessMode:ReadWriteOnce] resources:map[requests:map[cpu:100m memory:256Mi]] Name:redis _landscaper_metadata:map[chartrepository:stable releaseversion:5.5.5] image:bitnami/redis:3.2.8-r3]
[0001]  INFO  Applied desired state sucessfully created=1 deleted=0 updated=0
[0001]  WARN  Since dry-run is enabled, no actual actions have been performed

Convert *Component slices into maps

Components are uniquely identified by name. Current implementation consists of traversals to look up and x-ref Components by name. Behaviour is effectively a Map implemented on top of slices. Map is more natural, more LoC compact and more big-O time efficient.

Landscaper won't run on alpine:3.6

Curling the latest 1.0.5 binaries for linux amd64 won't run inside the alpine:3.6 image.
It did run in a slim image.

I have a feeling this is because the executable is dynamically linked... Looking into it now.

ldd landscaper
	/lib64/ld-linux-x86-64.so.2 (0x559eec9ae000)
	libpthread.so.0 => /lib64/ld-linux-x86-64.so.2 (0x559eec9ae000)
	libc.so.6 => /lib64/ld-linux-x86-64.so.2 (0x559eec9ae000)

We were able to resolve this by installing the following on alpine:

apk add libc6-compat

So basically, this comes down to alpine having muslibc.


Would it be possible to start compiling and statically linking against musl?
Are you open to a PR for that?

Using secrets for Datadog chart

This is my state file for Datadog Chart:

name: datadog
release:
  chart: stable/datadog:0.3.0
  version: 0.3.0
configuration:
  # Default values for datadog.
  image:
    repository: datadog/docker-dd-agent
    tag: latest
    pullPolicy: IfNotPresent

  datadog:
    ## You'll need to set this to your Datadog API key before the agent will run.
    ## ref: https://app.datadoghq.com/account/settings#agent/kubernetes
    ##
    apiKey: ""

    ## Set logging verbosity.
    ## ref: https://github.com/DataDog/docker-dd-agent#environment-variables
    ##
    logLevel: WARNING

  resources:
    requests:
      cpu: 100m
      memory: 128Mi
    limits:
      cpu: 256m
      memory: 512Mi
secrets:
  - api-key

and this is how run landscraper

API_KEY=343242342342  landscaper apply --dir charts --dry-run --namespace default

Unfortunately the secret API_KEY is not applied. Any idea?

Difference with helm upgrade

Hello!

I'm trying to understand the added value of Landscaper in comparison with simple helm upgrade.

Similar to Lanscaper, the upgrade can change a deployed release by applying the given values (-f or --set) to the given chart (chart reference or path to chart directory). And this can be added to your CI/CD chain to be triggered on merge.

So, what is the difference? and how do you see the combined usage of both of these solutions (if ever possible)?

Thank you,
Andrey

build issue

Hi,

Can you upload binary files to releases page instead of source code? I'm having trouble to build ... Thanks.

[INFO] --> Exporting golang.org/x/net
[INFO] --> Exporting golang.org/x/oauth2
[INFO] --> Exporting gopkg.in/validator.v2
[INFO] --> Exporting gopkg.in/yaml.v2
[INFO] --> Exporting k8s.io/kubernetes
[INFO] --> Exporting cloud.google.com/go
[INFO] --> Exporting golang.org/x/text
[INFO] --> Exporting google.golang.org/grpc
[INFO] Replacing existing vendor dependencies
[ERROR] Unable to export dependencies to vendor directory: symlink ../../../contrib/init/sysvinit-debian/docker.default /data/gowork/src/github.com/eneco/landscaper/vendor/github.com/docker/docker/hack/make/.build-deb/docker-engine.docker.default: operation not supported
Makefile:21: recipe for target 'bootstrap' failed
make: *** [bootstrap] Error 1

root@ubuntu16:/data/gowork/src/github.com/eneco/landscaper# ll /data/gowork/src/github.com/eneco/landscaper/vendor/github.com/docker/docker/hack/make/.build-deb/docker-engine.docker.default
ls: cannot access '/data/gowork/src/github.com/eneco/landscaper/vendor/github.com/docker/docker/hack/make/.build-deb/docker-engine.docker.default': No such file or directory

root@ubuntu16:/data/gowork/src/github.com/eneco/landscaper/vendor/github.com/docker/docker/hack/make/.build-deb# ll
total 13
drwxr-xr-x 2 root root 0 Apr 6 23:25 ./
drwxr-xr-x 2 root root 8192 Apr 6 23:25 ../
-rwxr-xr-x 1 root root 2 Apr 6 23:25 compat*
-rwxr-xr-x 1 root root 1238 Apr 6 23:25 control*

REST api?

The usage section of landscaper says "Landscaper consists of a core API and a command line interface (CLI) that consumes this API. "

Is this "core API" exposed through a REST interface?

Is there a (relatively) easy way to add/create one?

Add --no-cache option to apply

provide the ability to not use a cached chart in the event the cached copy is corrupted or re-deploying the same version.

landscaper apply keeps failing with incompatible helm versions

Have set up the Helm and Tiller with v2.3.1. helm version does report the expected version:

$ helm version
Client: &version.Version{SemVer:"v2.3.1", GitCommit:"32562a3040bb5ca690339b9840b6f60f8ce25da4", GitTreeState:"clean"}
Server: &version.Version{SemVer:"v2.3.1", GitCommit:"32562a3040bb5ca690339b9840b6f60f8ce25da4", GitTreeState:"clean"}
$ helm list
$

However, the landscaper apply shows the helmClientVersion=v2.4 and keeps failing:

$ landscaper apply test.yaml --namespace test -v
[2017-06-09T02:41:07Z] INFO This is Landscaper v1.0.6-rc.1 commit=3e47462b0fdff641b8b7dc6029f635de5a14126e tag=1.0.6-rc.1
[2017-06-09T02:41:07Z] INFO Apply landscape desired state dir= dryRun=false helmHome=/root/.helm namespace=test releasePrefix=test- verbose=true
[2017-06-09T02:41:07Z] DEBUG Setup Kubernetes Client
[2017-06-09T02:41:07Z] INFO Connected to Kubernetes kubernetesVersion=v1.6.4
[2017-06-09T02:41:07Z] DEBUG Setup Helm Client helmClientVersion=v2.4
[2017-06-09T02:41:07Z] DEBUG Create tiller tunnel tillerNamespace=kube-system
[2017-06-09T02:41:07Z] DEBUG Created tiller tunnel port=44217
[2017-06-09T02:41:07Z] INFO Connected to Tiller clientServerCompatible=false tillerVersion=v2.3.1
[2017-06-09T02:41:07Z] WARN Helm and Tiller report incompatible version numbers
[2017-06-09T02:41:07Z] INFO Obtain desired state from files files=[test.yaml]
[2017-06-09T02:41:07Z] DEBUG Read desired state from file file=test.yaml
...
[2017-06-09T02:41:07Z] DEBUG Desired state has been read n_components=1
[2017-06-09T02:41:07Z] INFO Obtain current state Helm Releases (Components) from Tiller
[2017-06-09T02:41:07Z] DEBUG listHelmReleases
[2017-06-09T02:41:07Z] ERROR Loading current state failed error=rpc error: code = Unknown desc = incompatible versions client: v2.4+unreleased server: v2.3.1
Error: rpc error: code = Unknown desc = incompatible versions client: v2.4+unreleased server: v2.3.1

Release.Version?

What is the release.version used for in a component definition?

release:
  version: 0.1.0

Request: --set flag

It would be nice to be able to use the --set flag with similar functionality to the Helm --set flag.

Provide landscaper generate command

Which creates a landscaper component template, given a chart reference. Assist with required values (upcoming Helm feature). Show defaults. etc.

Allow greater flexibility in populating Landscaper secrets

Superset of #42. I would love to have pluggable sources for secrets other than environment variables, such as a local file, Hashicorp's Vault, other remote K/V stores like Etcd/Consul, etc. Of course, you could wire up basically any of what I've mentioned to populate env vars with a little glue code, often surprisingly little. But env vars have some trade-offs that prevent them from being some user's first choice for sensitive data, myself included.

Helm and Tiller report incompatible version numbers

Hi,

I'm confused at "[0000] DEBUG Setup Helm Client helmClientVersion=v2.3.1", I'm using helm and tiller both v2.1.3, but why log says helmClientVersion=v2.3.1, is this mean I MUST use helm client with version 2.3.1? Thanks.

[0000] DEBUG  desired landscaper.Component{Name:"example-hello-world", Namespace:"example", Release:(*landscaper.Release)(0xc420180900), Configuration:landscaper.Configuration{"message":"Hello, Landscaped world!", "sleep":1, "Name":"hello-world", "_landscaper_metadata":map[string]interface {}{"chartrepository":"devops", "releaseversion":"0.1.0"}}, Secrets:landscaper.Secrets{}, SecretValues:landscaper.SecretValues{}}
[0000] DEBUG  Desired state has been read components=2 directory=example/landscape
[0000]  INFO  Obtain current state Helm Releases (Components) from Tiller
[0000] DEBUG  listHelmReleases
[0000] DEBUG  Setup Helm Client helmClientVersion=v2.3.1
[0000] DEBUG  Create tiller tunnel tillerNamespace=kube-system
E0504 14:40:20.408012    7197 portforward.go:209] Unable to create listener: Error listen tcp6 [::1]:22972: bind: cannot assign requested address
[0000] DEBUG  Created tiller tunnel port=22972
[0000]  INFO  Connected to Tiller clientServerCompatible=false tillerVersion=v2.1.3
[0000]  WARN  Helm and Tiller report incompatible version numbers
[0000] ERROR  Loading current state failed error=rpc error: code = 2 desc = client version is incompatible
Error: rpc error: code = 2 desc = client version is incompatible

root@myserver:/tmp/landscaper$ helm version
E0504 14:40:26.246994    7211 portforward.go:209] Unable to create listener: Error listen tcp6 [::1]:34390: bind: cannot assign requested address
Client: &version.Version{SemVer:"v2.1.3", GitCommit:"5cbc48fb305ca4bf68c26eb8d2a7eb363227e973", GitTreeState:"clean"}
Server: &version.Version{SemVer:"v2.1.3", GitCommit:"5cbc48fb305ca4bf68c26eb8d2a7eb363227e973", GitTreeState:"clean"}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.