mirror of https://github.com/hashicorp/consul
commit
891c4026c1
@ -0,0 +1,482 @@
|
||||
---
|
||||
layout: docs
|
||||
page_title: Consul Custom Resource Definitions (Beta)
|
||||
sidebar_title: Custom Resource Definitions <sup>(Beta)</sup>
|
||||
description: >-
|
||||
Consul now supports managing configuration entries via Kubernetes Custom Resources.
|
||||
These custom resource can be used to manage the configuration for workloads
|
||||
deployed within the cluster.
|
||||
---
|
||||
|
||||
# Custom Resource Definitions <sup>(beta)</sup>
|
||||
|
||||
## Overview
|
||||
|
||||
-> **This feature is currently in Beta.** It requires consul-helm >= 0.25.0 and
|
||||
consul >= 1.8.4.
|
||||
|
||||
We support managing Consul [configuration entries](/docs/agent/config-entries)
|
||||
via Kubernetes Custom Resources. Configuration entries are used to provide
|
||||
cluster-wide defaults for the service mesh.
|
||||
|
||||
We currently support the follow configuration entry kinds:
|
||||
|
||||
- [`proxy-defaults`](/docs/agent/config-entries/proxy-defaults)
|
||||
- [`service-defaults`](/docs/agent/config-entries/service-defaults)
|
||||
- [`service-splitter`](/docs/agent/config-entries/service-splitter)
|
||||
- [`service-router`](/docs/agent/config-entries/service-router)
|
||||
- [`service-resolver`](/docs/agent/config-entries/service-resolver)
|
||||
- [`service-intentions`](/docs/agent/config-entries/service-intentions) (requires Consul >= 1.9.0)
|
||||
|
||||
The following kinds are **not** currently supported:
|
||||
|
||||
- [`ingress-gateway`](/docs/agent/config-entries/ingress-gateway)
|
||||
- [`terminating-gateway`](/docs/agent/config-entries/terminating-gateway)
|
||||
|
||||
## Installation
|
||||
|
||||
Ensure you have version `0.25.0` of the helm chart:
|
||||
|
||||
```shell-session
|
||||
$ helm search repo hashicorp/consul
|
||||
NAME CHART VERSION APP VERSION DESCRIPTION
|
||||
hashicorp/consul 0.25.0 1.8.4 Official HashiCorp Consul Chart
|
||||
```
|
||||
|
||||
If you don't have `0.25.0`, you will need to update your helm repository cache:
|
||||
|
||||
```shell-session
|
||||
$ helm repo update
|
||||
Hang tight while we grab the latest from your chart repositories...
|
||||
...Successfully got an update from the "hashicorp" chart repository
|
||||
Update Complete. ⎈Happy Helming!⎈
|
||||
```
|
||||
|
||||
Next, you must configure consul-helm via your `values.yaml` to install the custom resource definitions
|
||||
and enable the controller that acts on them:
|
||||
|
||||
```yaml
|
||||
global:
|
||||
name: consul
|
||||
image: 'consul:1.9.0-beta1' # consul >= 1.8.4 must be used
|
||||
imageK8S: 'hashicorp/consul-k8s:0.19.0'
|
||||
|
||||
controller:
|
||||
enabled: true
|
||||
|
||||
connectInject:
|
||||
enabled: true
|
||||
```
|
||||
|
||||
Note that:
|
||||
|
||||
1. `controller.enabled: true` installs the CRDs and enables the controller.
|
||||
1. `global.image` must be a Consul version `>= 1.8.4`, e.g. `consul:1.8.4` or `consul:1.9.0-beta1`.
|
||||
1. `global.imageK8S` must be `>= 0.19.0`
|
||||
1. Configuration entries are used to configure Consul service mesh so it's also
|
||||
expected that `connectInject` will be enabled.
|
||||
|
||||
See [Install with Helm Chart](/docs/k8s/installation/install) for further installation
|
||||
instructions.
|
||||
|
||||
## Usage
|
||||
|
||||
Once installed, we can use `kubectl` to create and manage Consul's configuration entries.
|
||||
|
||||
### Create
|
||||
|
||||
We can create configuration entries via `kubectl apply`.
|
||||
|
||||
```shell-session
|
||||
$ cat <<EOF | kubectl apply -f -
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceDefaults
|
||||
metadata:
|
||||
name: foo
|
||||
spec:
|
||||
protocol: "http"
|
||||
EOF
|
||||
|
||||
servicedefaults.consul.hashicorp.com/foo created
|
||||
```
|
||||
|
||||
See [Specifications](#specifications) for detailed schema documentation.
|
||||
|
||||
### Get
|
||||
|
||||
We can use `kubectl get [kind] [name]` to get the status of the configuration entry:
|
||||
|
||||
```shell-session
|
||||
$ kubectl get servicedefaults foo
|
||||
NAME SYNCED
|
||||
foo True
|
||||
```
|
||||
|
||||
The `SYNCED` status shows whether the configuration entry was successfully created
|
||||
in Consul.
|
||||
|
||||
### Describe
|
||||
|
||||
We can use `kubectl describe [kind] [name]` to investigate the status of the
|
||||
configuration entry. If `SYNCED` is false, the status will contain the reason
|
||||
why.
|
||||
|
||||
```shell-session
|
||||
$ kubectl describe servicedefaults foo
|
||||
Status:
|
||||
Conditions:
|
||||
Last Transition Time: 2020-10-09T21:15:50Z
|
||||
Status: True
|
||||
Type: Synced
|
||||
```
|
||||
|
||||
### Edit
|
||||
|
||||
We can use `kubectl edit [kind] [name]` to edit the configuration entry:
|
||||
|
||||
```shell
|
||||
$ kubectl edit servicedefaults foo
|
||||
# change protocol: http => protocol: tcp
|
||||
servicedefaults.consul.hashicorp.com/foo edited
|
||||
```
|
||||
|
||||
We can then use `kubectl get` to ensure the change was synced to Consul:
|
||||
|
||||
```shell-session
|
||||
$ kubectl get servicedefaults foo
|
||||
NAME SYNCED
|
||||
foo True
|
||||
```
|
||||
|
||||
### Delete
|
||||
|
||||
We can use `kubectl delete [kind] [name]` to delete the configuration entry:
|
||||
|
||||
```shell-session
|
||||
$ kubectl delete servicedefaults foo
|
||||
servicedefaults.consul.hashicorp.com "foo" deleted
|
||||
```
|
||||
|
||||
We can then use `kubectl get` to ensure the configuration entry was deleted:
|
||||
|
||||
```shell-session
|
||||
$ kubectl get servicedefaults foo
|
||||
Error from server (NotFound): servicedefaults.consul.hashicorp.com "foo" not found
|
||||
```
|
||||
|
||||
#### Delete Hanging
|
||||
|
||||
If running `kubectl delete` hangs without exiting, there may be
|
||||
a requirement inside Consul that prevents that configuration entry from being
|
||||
deleted. For example, if you set the protocol of your service to `http` via `ServiceDefaults` and then
|
||||
create a `ServiceSplitter`, you won't be able to delete the `ServiceDefaults`.
|
||||
|
||||
This is because by deleting the `ServiceDefaults` config, you are setting the
|
||||
protocol back to the default which is `tcp`. Since `ServiceSplitter` requires
|
||||
that the service has an `http` protocol, Consul will not allow the `ServiceDefaults`
|
||||
to be deleted since that would put Consul into a broken state.
|
||||
|
||||
In order to delete the `ServiceDefaults` config you would need to first delete
|
||||
the `ServiceSplitter`.
|
||||
|
||||
## Specifications
|
||||
|
||||
### ProxyDefaults
|
||||
|
||||
[proxy-defaults](/docs/agent/config-entries/proxy-defaults)
|
||||
configures global defaults across all proxies.
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ProxyDefaults
|
||||
metadata:
|
||||
name: global
|
||||
spec:
|
||||
config:
|
||||
envoy_tracing_json: '{"http":{"name":"envoy.zipkin","config":{"collector_cluster":"zipkin","collector_endpoint":"/api/v1/spans","shared_span_context":false}}}'
|
||||
expose:
|
||||
checks: true
|
||||
paths:
|
||||
- listenerPort: 80
|
||||
localPathPort: 42
|
||||
path: /test/path
|
||||
protocol: tcp
|
||||
- listenerPort: 8080
|
||||
localPathPort: 4201
|
||||
path: /root/test/path
|
||||
protocol: https
|
||||
meshGateway:
|
||||
mode: local
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. There can only be one `ProxyDefaults` resource and its name **must** be `global`.
|
||||
1. Keys under `spec.config` will need to use `snake_case`, not `camelCase`, because
|
||||
this config is passed directly to Envoy which uses `snake_case`, e.g.
|
||||
```yaml
|
||||
spec:
|
||||
config:
|
||||
envoy_statsd_url: 'udp://127.0.0.1:8125'
|
||||
```
|
||||
1. See [proxy-defaults](/docs/agent/config-entries/proxy-defaults) for full
|
||||
documentation on this config entry.
|
||||
|
||||
### ServiceDefaults
|
||||
|
||||
[service-defaults](/docs/agent/config-entries/service-defaults)
|
||||
configures a specific service.
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceDefaults
|
||||
metadata:
|
||||
name: your-service-name
|
||||
spec:
|
||||
protocol: https
|
||||
meshGateway:
|
||||
mode: local
|
||||
expose:
|
||||
checks: true
|
||||
paths:
|
||||
- listenerPort: 80
|
||||
path: /path
|
||||
localPathPort: 9000
|
||||
protocol: tcp
|
||||
- listenerPort: 8080
|
||||
path: /another-path
|
||||
localPathPort: 9091
|
||||
protocol: http2
|
||||
externalSNI: external-sni
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. The name of the service that this `ServiceDefaults` configures is set by
|
||||
`metadata.name`.
|
||||
1. See [service-defaults](/docs/agent/config-entries/service-defaults) for full
|
||||
documentation on this config entry.
|
||||
|
||||
### ServiceIntentions <sup>(Beta)</sup>
|
||||
|
||||
[service-intentions](/docs/agent/config-entries/service-intentions)
|
||||
configures traffic authorization for a destination service.
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceIntentions
|
||||
metadata:
|
||||
name: my-intention
|
||||
spec:
|
||||
destination:
|
||||
name: your-service-name
|
||||
sources:
|
||||
- name: svc1
|
||||
namespace: test
|
||||
action: allow
|
||||
permissions: []
|
||||
description: allow access from svc1
|
||||
- name: '*'
|
||||
namespace: not-test
|
||||
action: deny
|
||||
permissions: []
|
||||
description: disallow access from namespace not-test
|
||||
- name: svc-2
|
||||
namespace: bar
|
||||
action: ''
|
||||
permissions:
|
||||
- action: allow
|
||||
http:
|
||||
pathExact: /foo
|
||||
pathPrefix: /bar
|
||||
pathRegex: /baz
|
||||
header:
|
||||
- name: header
|
||||
present: true
|
||||
exact: exact
|
||||
prefix: prefix
|
||||
suffix: suffix
|
||||
regex: regex
|
||||
invert: true
|
||||
methods:
|
||||
- GET
|
||||
- PUT
|
||||
description: an L7 config
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. This resource is only supported in Consul 1.9.0.
|
||||
1. Unlike the other configuration entries, the value of `metadata.name` does not
|
||||
define which service the intention applies to. It can be set to any value
|
||||
however we recommend setting it to the name of the destination service the
|
||||
intention is configuring.
|
||||
|
||||
Instead, the name of the service this intention
|
||||
is configuring is set in `spec.destination.name`.
|
||||
|
||||
1. Wildcard intentions can be created by setting `spec.destination.name` to `*` and/or
|
||||
`spec.sources[].name` to `*`. For example to create a `deny` intention that applies
|
||||
to all services:
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceIntentions
|
||||
metadata:
|
||||
name: deny-all
|
||||
spec:
|
||||
destination:
|
||||
name: *
|
||||
sources:
|
||||
- name: *
|
||||
action: deny
|
||||
```
|
||||
|
||||
1. See [service-intentions](/docs/agent/config-entries/service-intentions) for full
|
||||
documentation on this config entry.
|
||||
|
||||
### ServiceResolver
|
||||
|
||||
[service-resolver](/docs/agent/config-entries/service-resolver)
|
||||
configures which service instances should satisfy Connect upstream discovery requests for a given service name.
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceResolver
|
||||
metadata:
|
||||
name: your-service-name
|
||||
spec:
|
||||
defaultSubset: default_subset
|
||||
subsets:
|
||||
subset1:
|
||||
filter: filter1
|
||||
onlyPassing: true
|
||||
subset2:
|
||||
filter: filter2
|
||||
redirect:
|
||||
service: redirect
|
||||
serviceSubset: redirect_subset
|
||||
namespace: redirect_namespace
|
||||
datacenter: redirect_datacenter
|
||||
failover:
|
||||
failover1:
|
||||
service: failover1
|
||||
serviceSubset: failover_subset1
|
||||
namespaces: failover_namespace1
|
||||
datacenters:
|
||||
- failover1_dc1
|
||||
- failover1_dc2
|
||||
failover2:
|
||||
service: failover2
|
||||
serviceSubset: failover_subset2
|
||||
namespaces: failover_namespace2
|
||||
datacenters:
|
||||
- failover2_dc1
|
||||
- failover2_dc2
|
||||
connectTimeout: 1000000000
|
||||
loadBalancer:
|
||||
policy: policy
|
||||
ringHashConfig:
|
||||
minimumRingSize: 1
|
||||
maximumRingSize: 2
|
||||
leastRequestConfig:
|
||||
choiceCount: 1
|
||||
hashPolicies:
|
||||
- field: field
|
||||
fieldValue: value
|
||||
cookieConfig:
|
||||
session: true
|
||||
ttl: 1
|
||||
path: path
|
||||
sourceIP: true
|
||||
terminal: true
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. The name of the service that this `ServiceResolver` configures is set by
|
||||
`metadata.name`.
|
||||
1. See [service-resolver](/docs/agent/config-entries/service-resolver) for full
|
||||
documentation on this config entry.
|
||||
|
||||
### ServiceRouter
|
||||
|
||||
[service-router](/docs/agent/config-entries/service-router)
|
||||
configures traffic routing and manipulation at networking layer 7 (e.g. HTTP).
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceRouter
|
||||
metadata:
|
||||
name: your-service-name
|
||||
spec:
|
||||
routes:
|
||||
- match:
|
||||
http:
|
||||
pathExact: pathExact
|
||||
pathPrefix: pathPrefix
|
||||
pathRegex: pathRegex
|
||||
header:
|
||||
- name: name
|
||||
present: true
|
||||
exact: exact
|
||||
prefix: prefix
|
||||
suffix: suffix
|
||||
regex: regex
|
||||
invert: true
|
||||
queryParam:
|
||||
- name: name
|
||||
present: true
|
||||
exact: exact
|
||||
regex: regex
|
||||
methods:
|
||||
- method1
|
||||
- method2
|
||||
destination:
|
||||
service: service
|
||||
serviceSubset: serviceSubset
|
||||
namespace: namespace
|
||||
prefixRewrite: prefixRewrite
|
||||
requestTimeout: 1000000000
|
||||
numRetries: 1
|
||||
retryOnConnectFailure: true
|
||||
retryOnStatusCodes:
|
||||
- 500
|
||||
- 400
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. The name of the service that this `ServiceRouter` configures is set by
|
||||
`metadata.name`.
|
||||
1. See [service-router](/docs/agent/config-entries/service-router) for full
|
||||
documentation on this config entry.
|
||||
|
||||
### ServiceSplitter
|
||||
|
||||
[service-splitter](/docs/agent/config-entries/service-splitter)
|
||||
configures splitting incoming requests across different subsets of a single service.
|
||||
|
||||
```yaml
|
||||
apiVersion: consul.hashicorp.com/v1alpha1
|
||||
kind: ServiceSplitter
|
||||
metadata:
|
||||
name: your-service-name
|
||||
spec:
|
||||
splits:
|
||||
- weight: 50.1
|
||||
service: foo
|
||||
serviceSubset: bar
|
||||
namespace: baz
|
||||
- weight: 49.9
|
||||
service: foo
|
||||
serviceSubset: bar
|
||||
namespace: baz
|
||||
```
|
||||
|
||||
Notes:
|
||||
|
||||
1. The name of the service that this `ServiceSplitter` configures is set by
|
||||
`metadata.name`.
|
||||
1. See [service-splitter](/docs/agent/config-entries/service-splitter) for full
|
||||
documentation on this config entry.
|
Loading…
Reference in new issue