Skip to content
This repository has been archived by the owner on May 16, 2023. It is now read-only.

Commit

Permalink
Merge branch 'master' into feature/metrics-cluster-role-events
Browse files Browse the repository at this point in the history
  • Loading branch information
Crazybus authored Sep 18, 2019
2 parents 580b166 + 8502b6f commit c6c220e
Show file tree
Hide file tree
Showing 18 changed files with 303 additions and 19 deletions.
5 changes: 5 additions & 0 deletions .ci/views/views.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
- view:
name: 'Helm Charts'
regex: '^elastic[-+]helm-charts.*$'
view-type: list
62 changes: 50 additions & 12 deletions elasticsearch/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,7 @@ helm install --name elasticsearch elastic/elasticsearch --set imageTag=7.3.0
| `schedulerName` | Name of the [alternate scheduler](https://kubernetes.io/docs/tasks/administer-cluster/configure-multiple-schedulers/#specify-schedulers-for-pods) | `nil` |
| `masterTerminationFix` | A workaround needed for Elasticsearch < 7.2 to prevent master status being lost during restarts [#63](https://github.com/elastic/helm-charts/issues/63) | `false` |
| `lifecycle` | Allows you to add lifecycle configuration. See [values.yaml](./values.yaml) for an example of the formatting. | `{}` |
| `keystore` | Allows you map Kubernetes secrets into the keystore. See the [config example](/elasticsearch/examples/config/values.yaml) and [how to use the keystore](#how-to-use-the-keystore) | `[]` |

## Try it out

Expand Down Expand Up @@ -171,18 +172,55 @@ There are a couple reasons we recommend this.

#### How to use the keystore?

1. Create a Kubernetes secret containing the [keystore](https://www.elastic.co/guide/en/elasticsearch/reference/current/secure-settings.html)
```
$ kubectl create secret generic elasticsearch-keystore --from-file=./elasticsearch.keystore
```
2. Mount it into the container via `secretMounts`
```
secretMounts:
- name: elasticsearch-keystore
secretName: elasticsearch-keystore
path: /usr/share/elasticsearch/config/elasticsearch.keystore
subPath: elasticsearch.keystore
```

##### Basic example

Create the secret, the key name needs to be the keystore key path. In this example we will create a secret from a file and from a literal string.

```
kubectl create secret generic encryption_key --from-file=xpack.watcher.encryption_key=./watcher_encryption_key
kubectl create secret generic slack_hook --from-literal=xpack.notification.slack.account.monitoring.secure_url='https://hooks.slack.com/services/asdasdasd/asdasdas/asdasd'
```

To add these secrets to the keystore:
```
keystore:
- secretName: encryption_key
- secretName: slack_hook
```

##### Multiple keys

All keys in the secret will be added to the keystore. To create the previous example in one secret you could also do:

```
kubectl create secret generic keystore_secrets --from-file=xpack.watcher.encryption_key=./watcher_encryption_key --from-literal=xpack.notification.slack.account.monitoring.secure_url='https://hooks.slack.com/services/asdasdasd/asdasdas/asdasd'
```

```
keystore:
- secretName: keystore_secrets
```

##### Custom paths and keys

If you are using these secrets for other applications (besides the Elasticsearch keystore) then it is also possible to specify the keystore path and which keys you want to add. Everything specified under each `keystore` item will be passed through to the `volumeMounts` section for [mounting the secret](https://kubernetes.io/docs/concepts/configuration/secret/#using-secrets). In this example we will only add the `slack_hook` key from a secret that also has other keys. Our secret looks like this:

```
kubectl create secret generic slack_secrets --from-literal=slack_channel='#general' --from-literal=slack_hook='https://hooks.slack.com/services/asdasdasd/asdasdas/asdasd'
```

We only want to add the `slack_hook` key to the keystore at path `xpack.notification.slack.account.monitoring.secure_url`.

```
keystore:
- secretName: slack_secrets
items:
- key: slack_hook
path: xpack.notification.slack.account.monitoring.secure_url
```

You can also take a look at the [config example](/elasticsearch/examples/config/) which is used as part of the automated testing pipeline.

#### How to enable snapshotting?

Expand Down
19 changes: 19 additions & 0 deletions elasticsearch/examples/config/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
default: test
include ../../../helpers/examples.mk

RELEASE := helm-es-config

install:
helm upgrade --wait --timeout=600 --install $(RELEASE) --values ./values.yaml ../../ ; \

secrets:
kubectl delete secret elastic-config-credentials elastic-config-secret elastic-config-slack elastic-config-custom-path || true
kubectl create secret generic elastic-config-credentials --from-literal=password=changeme --from-literal=username=elastic
kubectl create secret generic elastic-config-slack --from-literal=xpack.notification.slack.account.monitoring.secure_url='https://hooks.slack.com/services/asdasdasd/asdasdas/asdasd'
kubectl create secret generic elastic-config-secret --from-file=xpack.watcher.encryption_key=./watcher_encryption_key
kubectl create secret generic elastic-config-custom-path --from-literal=slack_url='https://hooks.slack.com/services/asdasdasd/asdasdas/asdasd' --from-literal=thing_i_don_tcare_about=test

test: secrets install goss

purge:
helm del --purge $(RELEASE)
3 changes: 3 additions & 0 deletions elasticsearch/examples/config/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Config

An example testing suite for testing some of the optional features of this chart.
26 changes: 26 additions & 0 deletions elasticsearch/examples/config/test/goss.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
http:
http://localhost:9200/_cluster/health:
status: 200
timeout: 2000
body:
- 'green'
- '"number_of_nodes":1'
- '"number_of_data_nodes":1'

http://localhost:9200:
status: 200
timeout: 2000
body:
- '"cluster_name" : "config"'
- '"name" : "config-master-0"'
- 'You Know, for Search'

command:
"elasticsearch-keystore list":
exit-status: 0
stdout:
- keystore.seed
- bootstrap.password
- xpack.notification.slack.account.monitoring.secure_url
- xpack.notification.slack.account.otheraccount.secure_url
- xpack.watcher.encryption_key
31 changes: 31 additions & 0 deletions elasticsearch/examples/config/values.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
---

clusterName: "config"
replicas: 1

extraEnvs:
- name: ELASTIC_PASSWORD
valueFrom:
secretKeyRef:
name: elastic-credentials
key: password
- name: ELASTIC_USERNAME
valueFrom:
secretKeyRef:
name: elastic-credentials
key: username

# This is just a dummy file to make sure that
# the keystore can be mounted at the same time
# as a custom elasticsearch.yml
esConfig:
elasticsearch.yml: |
path.data: /usr/share/elasticsearch/data
keystore:
- secretName: elastic-config-secret
- secretName: elastic-config-slack
- secretName: elastic-config-custom-path
items:
- key: slack_url
path: xpack.notification.slack.account.otheraccount.secure_url
1 change: 1 addition & 0 deletions elasticsearch/examples/config/watcher_encryption_key
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
supersecret
45 changes: 45 additions & 0 deletions elasticsearch/templates/statefulset.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,14 @@ spec:
configMap:
name: {{ template "uname" . }}-config
{{- end }}
{{- if .Values.keystore }}
- name: keystore
emptyDir: {}
{{- range .Values.keystore }}
- name: keystore-{{ .secretName }}
secret: {{ toYaml . | nindent 12 }}
{{- end }}
{{ end }}
{{- if .Values.extraVolumes }}
{{ tpl .Values.extraVolumes . | indent 8 }}
{{- end }}
Expand All @@ -129,6 +137,38 @@ spec:
resources:
{{ toYaml .Values.initResources | indent 10 }}
{{- end }}
{{ if .Values.keystore }}
- name: keystore
image: "{{ .Values.image }}:{{ .Values.imageTag }}"
command:
- sh
- -c
- |
#!/usr/bin/env bash
set -euo pipefail
elasticsearch-keystore create
for i in /tmp/keystoreSecrets/*/*; do
key=$(basename $i)
echo "Adding file $i to keystore key $key"
elasticsearch-keystore add-file "$key" "$i"
done
# Add the bootstrap password since otherwise the Elasticsearch entrypoint tries to do this on startup
[ ! -z "$ELASTIC_PASSWORD" ] && echo "$ELASTIC_PASSWORD" | elasticsearch-keystore add -x bootstrap.password
cp -a /usr/share/elasticsearch/config/elasticsearch.keystore /tmp/keystore/
env: {{ toYaml .Values.extraEnvs | nindent 10 }}
resources: {{ toYaml .Values.initResources | nindent 10 }}
volumeMounts:
- name: keystore
mountPath: /tmp/keystore
{{- range .Values.keystore }}
- name: keystore-{{ .secretName }}
mountPath: /tmp/keystoreSecrets/{{ .secretName }}
{{- end }}
{{ end }}
{{- if .Values.extraInitContainers }}
{{ tpl .Values.extraInitContainers . | indent 6 }}
{{- end }}
Expand Down Expand Up @@ -219,6 +259,11 @@ spec:
- name: "{{ template "uname" . }}"
mountPath: /usr/share/elasticsearch/data
{{- end }}
{{ if .Values.keystore }}
- name: keystore
mountPath: /usr/share/elasticsearch/config/elasticsearch.keystore
subPath: elasticsearch.keystore
{{ end }}
{{- range .Values.secretMounts }}
- name: {{ .name }}
mountPath: {{ .path }}
Expand Down
106 changes: 106 additions & 0 deletions elasticsearch/tests/elasticsearch_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -793,3 +793,109 @@ def test_adding_pod_labels():
'''
r = helm_template(config)
assert r['statefulset'][uname]['metadata']['labels']['app.kubernetes.io/name'] == 'elasticsearch'

def test_keystore_enable():
config = ''

r = helm_template(config)
s = r['statefulset'][uname]['spec']['template']['spec']

assert s['volumes'] == None

config = '''
keystore:
- secretName: test
'''

r = helm_template(config)
s = r['statefulset'][uname]['spec']['template']['spec']

assert {'name': 'keystore', 'emptyDir': {}} in s['volumes']

def test_keystore_init_container():
config = ''

r = helm_template(config)
i = r['statefulset'][uname]['spec']['template']['spec']['initContainers'][-1]

assert i['name'] != 'keystore'

config = '''
keystore:
- secretName: test
'''

r = helm_template(config)
i = r['statefulset'][uname]['spec']['template']['spec']['initContainers'][-1]

assert i['name'] == 'keystore'

def test_keystore_mount():
config = '''
keystore:
- secretName: test
'''

r = helm_template(config)
s = r['statefulset'][uname]['spec']['template']['spec']
assert s['containers'][0]['volumeMounts'][-1] == {
'mountPath': '/usr/share/elasticsearch/config/elasticsearch.keystore',
'subPath': 'elasticsearch.keystore',
'name': 'keystore'
}

def test_keystore_init_volume_mounts():
config = '''
keystore:
- secretName: test
- secretName: test-with-custom-path
items:
- key: slack_url
path: xpack.notification.slack.account.otheraccount.secure_url
'''
r = helm_template(config)
s = r['statefulset'][uname]['spec']['template']['spec']
assert s['initContainers'][-1]['volumeMounts'] == [
{
'mountPath': '/tmp/keystore',
'name': 'keystore'
},
{
'mountPath': '/tmp/keystoreSecrets/test',
'name': 'keystore-test'
},
{
'mountPath': '/tmp/keystoreSecrets/test-with-custom-path',
'name': 'keystore-test-with-custom-path'
}
]

def test_keystore_volumes():
config = '''
keystore:
- secretName: test
- secretName: test-with-custom-path
items:
- key: slack_url
path: xpack.notification.slack.account.otheraccount.secure_url
'''
r = helm_template(config)
s = r['statefulset'][uname]['spec']['template']['spec']

assert {
'name': 'keystore-test',
'secret': {
'secretName': 'test'
}
} in s['volumes']

assert {
'name': 'keystore-test-with-custom-path',
'secret': {
'secretName': 'test-with-custom-path',
'items': [{
'key': 'slack_url',
'path': 'xpack.notification.slack.account.otheraccount.secure_url'
}]
}
} in s['volumes']
2 changes: 2 additions & 0 deletions elasticsearch/values.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -210,3 +210,5 @@ lifecycle: {}

sysctlInitContainer:
enabled: true

keystore: []
3 changes: 2 additions & 1 deletion helpers/matrix.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ CHART:
- metricbeat
ES_SUITE:
- default
- config
- multi
- oss
- security
Expand All @@ -26,6 +27,6 @@ METRICBEAT_SUITE:
- security
- 6.x
KUBERNETES_VERSION:
- '1.11'
- '1.12'
- '1.13'
- '1.14'
2 changes: 1 addition & 1 deletion helpers/terraform/main.tf
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
provider "google" {
project = "${var.project}"
region = "${var.primary_region}"
version = "1.13.0"
version = "2.13.0"
}

terraform {
Expand Down
3 changes: 2 additions & 1 deletion metricbeat/examples/default/test/goss-metrics.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ http:
timeout: 2000
body:
- 'metricbeat-7.3.0'
http://elasticsearch-master:9200/_search?q=metricset.name:state_deployment:

'http://elasticsearch-master:9200/_search?q=metricset.name:state_container%20AND%20kubernetes.container.name:metricbeat':
status: 200
timeout: 2000
body:
Expand Down
2 changes: 1 addition & 1 deletion metricbeat/examples/default/test/goss.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ http:
timeout: 2000
body:
- 'metricbeat-7.3.0'
http://elasticsearch-master:9200/_search?q=metricset.name:container:
'http://elasticsearch-master:9200/_search?q=metricset.name:container%20AND%20kubernetes.container.name:metricbeat':
status: 200
timeout: 2000
body:
Expand Down
Loading

0 comments on commit c6c220e

Please sign in to comment.