The post Introduction to Kustomize, Part 1: Creating a Kubernetes app out of multiple pieces appeared first on Mirantis | Pure Play Open Cloud.
Kustomize is a tool that lets you create an entire Kubernetes application out of individual pieces — without touching the YAML for the individual components. For example, you can combine pieces from different sources, keep your customizations — or kustomizations, as the case may be — in source control, and create overlays for specific situations. And it will be part of Kubernetes 1.14.
Kustomize enables you to do that by creating a file that ties everything together, or optionally includes “overrides” for individual parameters.
Let’s see how it works.
Curious about what else is new in Kubernetes 1.14? Join us for a live webinar on March 21.
Installing Kustomize
The first step, of course, is to install Kustomize. It’s easy if you’re on MacOS:
brew install kustomize
If not, you can install from go:
go get sigs.k8s.io/kustomize
Or you can install the latest from source:
opsys=linux # or darwin, or windows
curl -s https://api.github.com/repos/kubernetes-sigs/kustomize/releases/latest |
grep browser_download |
grep $opsys |
cut -d ‘”‘ -f 4 |
xargs curl -O -L
mv kustomize_*_${opsys}_amd64 kustomize
chmod u+x kustomize
To make sure it’s installed, go ahead and check the version:
$ kustomize version
Version: {KustomizeVersion:v2.0.2 GitCommit:b67179e951ebe11d00125bdf3c2670e88dca8817 BuildDate:2019-02-25T21:36:48+00:00 GoOs:darwin GoArch:amd64}
OK, now we’re ready to go!
Combining specs into a single app
One of the most common uses for Kustomize is to take multiple objects and combine them into a single application with common labels. For example, let’s say you want to deploy WordPress, and you find two Kubernetes manifests on the web. Let’s start by creating a directory to serve as a base directory:
KUSTOM_HOME=$(mktemp -d)
BASE=$KUSTOM_HOME/base
mkdir $BASE
WORDPRESS_HOME=$BASE/wordpress
mkdir $WORDPRESS_HOME
cd $WORDPRESS_HOME
Now let’s look at the manifests. One is for the deployment of WordPress itself. Let’s save that as $WORDPRESS_HOME/deployment.yaml.
apiVersion: apps/v1beta2
kind: Deployment
metadata:
name: wordpress
labels:
app: wordpress
spec:
selector:
matchLabels:
app: wordpress
strategy:
type: Recreate
template:
metadata:
labels:
app: wordpress
spec:
containers:
– image: wordpress:4.8-apache
name: wordpress
ports:
– containerPort: 80
name: wordpress
volumeMounts:
– name: wordpress-persistent-storage
mountPath: /var/www/html
volumes:
– name: wordpress-persistent-storage
emptyDir: {}
The second is a service to expose it. We’ll save it as $WORDPRESS_HOME/service.yaml.
apiVersion: v1
kind: Service
metadata:
name: wordpress
labels:
app: wordpress
spec:
ports:
– port: 80
selector:
app: wordpress
type: LoadBalancer
That all seems reasonable, and if we can put both of these files in a directory called wordpress and run:
$ kubectl apply -f $WORDPRESS_HOME
deployment.apps “wordpress” created
service “wordpress” created
Before we move on, let’s go ahead and clean that up:
$ kubectl delete -f $WORDPRESS_HOME
Now if you look at the definitions, you’ll notice that both resources show an app label of wordpress. If you wanted to deploy them with a label of, say, app:my-wordpress, you’d either have to add parameters on the command line or edit the files — which does away with the advantage of reusing the files.
Instead, we can use Kustomize to combine them into a single file — including the desired app label — without touching the originals.
We start by creating the file $WORDPRESS_HOME/kustomize.yaml and adding the following:
commonLabels:
app: my-wordpress
resources:
– deployment.yaml
– service.yaml
This is a very simple file that just says that we want to add a common label — app: my-wordpress — to the resources defined in deployment.yaml and service.yaml. Now we can use Kustomize to actually build the new YAML:
$ kustomize build $WORDPRESS_HOME
apiVersion: v1
kind: Service
metadata:
labels:
app: my-wordpress
name: wordpress
spec:
ports:
– port: 80
selector:
app: my-wordpress
type: LoadBalancer
—
apiVersion: apps/v1beta2
kind: Deployment
metadata:
labels:
app: my-wordpress
name: wordpress
spec:
selector:
matchLabels:
app: my-wordpress
strategy:
type: Recreate
template:
metadata:
labels:
app: my-wordpress
spec:
containers:
– image: wordpress:4.8-apache
name: wordpress
ports:
– containerPort: 80
name: wordpress
volumeMounts:
– mountPath: /var/www/html
name: wordpress-persistent-storage
volumes:
– emptyDir: {}
name: wordpress-persistent-storage
The output is the concatenation of YAML documents for all of the resources we specified, with the common labels added. You can output that to a file, or pipe it directly into kubectl. (We’ll cover that in Using Kustomize with kubectl.
Multiple directories
Now, that’s all great, but WordPress won’t run without a database. Fortunately, we have a set of similar files for setting up MySQL. Unfortunately, they have the same names as the files we have for WordPress, and remember, we don’t want to have to alter any of the files, so we need a way to pull from multiple directories. We can do that by creating multiple “bases”.
So we’ll start by creating a new directory:
MYSQL_HOME=$BASE/mysql
mkdir $MYSQL_HOME
cd $MYSQL_HOME
We’ll add three files to it. The first is a $MYSQL_HOME/deployment.yaml:
apiVersion: apps/v1beta2
kind: Deployment
metadata:
name: mysql
labels:
app: mysql
spec:
selector:
matchLabels:
app: mysql
strategy:
type: Recreate
template:
metadata:
labels:
app: mysql
spec:
containers:
– image: mysql:5.6
name: mysql
env:
– name: MYSQL_ROOT_PASSWORD
valueFrom:
secretKeyRef:
name: mysql-pass
key: password
ports:
– containerPort: 3306
name: mysql
volumeMounts:
– name: mysql-persistent-storage
mountPath: /var/lib/mysql
volumes:
– name: mysql-persistent-storage
emptyDir: {}
The second is $MYSQL_HOME/service.yaml:
apiVersion: v1
kind: Service
metadata:
name: mysql
labels:
app: mysql
spec:
ports:
– port: 3306
selector:
app: mysql
And finally $MYSQL_HOME/secret.yaml to hold the database username and password:
apiVersion: v1
kind: Secret
metadata:
name: mysql-pass
type: Opaque
data:
# Default password is “admin”.
password: YWRtaW4=
And we’ll add a Kustomization file, $MYSQL_HOME/kustomization.yaml, them together:
resources:
– deployment.yaml
– service.yaml
– secret.yaml
Now we need to tie the two directories together. First let’s clean up $WORDPRESS_HOME/kustomization.yaml to remove the labels so that it only references the resources:
resources:
– deployment.yaml
– service.yaml
Now we need to add a new kustomization file to the base directory at $BASE/kustomization.yaml:
commonLabels:
app: my-wordpress
bases:
– ./wordpress
– ./mysql
So we’ve moved our labels declaration out to this main file and defined the two base directories we’re working with. Now if we run the build ….
kustomize build $BASE
We can see that all of the files are gathered and the label is added to all of them:
apiVersion: v1
data:
password: YWRtaW4=
kind: Secret
metadata:
labels:
app: my-wordpress
name: mysql-pass
type: Opaque
—
apiVersion: v1
kind: Service
metadata:
labels:
app: my-wordpress
name: mysql
spec:
ports:
– port: 3306
selector:
app: my-wordpress
—
apiVersion: v1
kind: Service
metadata:
labels:
app: my-wordpress
name: wordpress
spec:
ports:
– port: 80
selector:
app: my-wordpress
type: LoadBalancer
—
apiVersion: apps/v1beta2
kind: Deployment
metadata:
labels:
app: my-wordpress
name: mysql
spec:
selector:
matchLabels:
app: my-wordpress
strategy:
type: Recreate
template:
metadata:
labels:
app: my-wordpress
spec:
containers:
– env:
– name: MYSQL_ROOT_PASSWORD
valueFrom:
secretKeyRef:
key: password
name: mysql-pass
image: mysql:5.6
name: mysql
ports:
– containerPort: 3306
name: mysql
volumeMounts:
– mountPath: /var/lib/mysql
name: mysql-persistent-storage
volumes:
– emptyDir: {}
name: mysql-persistent-storage
—
apiVersion: apps/v1beta2
kind: Deployment
metadata:
labels:
app: my-wordpress
name: wordpress
spec:
selector:
matchLabels:
app: my-wordpress
strategy:
type: Recreate
template:
metadata:
labels:
app: my-wordpress
spec:
containers:
– image: wordpress:4.8-apache
name: wordpress
ports:
– containerPort: 80
name: wordpress
volumeMounts:
– mountPath: /var/www/html
name: wordpress-persistent-storage
volumes:
– emptyDir: {}
name: wordpress-persistent-storage
OK, so now we’ve gathered multiple components, but what happens if we need to change something? Let’s look at that in part 2.
The post Introduction to Kustomize, Part 1: Creating a Kubernetes app out of multiple pieces appeared first on Mirantis | Pure Play Open Cloud.
Quelle: Mirantis