Convert site to Hugo (#8316)

This commit converts content and layout to use Hugo.
This commit is contained in:
Bjørn Erik Pedersen
2018-05-05 18:00:51 +02:00
committed by k8s-ci-robot
parent 7745f0e0c5
commit 7f3b633aa0
2327 changed files with 10928 additions and 171503 deletions
@@ -0,0 +1,4 @@
FROM node:6.9.2
EXPOSE 8080
COPY server.js .
CMD node server.js
@@ -0,0 +1,5 @@
---
title: "Stateless Applications"
weight: 90
---
@@ -0,0 +1,21 @@
apiVersion: apps/v1
kind: Deployment
metadata:
name: nginx-deployment
spec:
selector:
matchLabels:
app: nginx
replicas: 2 # tells deployment to run 2 pods matching the template
template: # create pods using pod definition in this template
metadata:
# unlike pod-nginx.yaml, the name is not included in the meta data as a unique name is
# generated from the deployment name
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:1.7.9
ports:
- containerPort: 80
@@ -0,0 +1,161 @@
---
title: Exposing an External IP Address to Access an Application in a Cluster
content_template: templates/tutorial
---
{{% capture overview %}}
This page shows how to create a Kubernetes Service object that exposes an
external IP address.
{{% /capture %}}
{{% capture prerequisites %}}
* Install [kubectl](/docs/tasks/tools/install-kubectl/).
* Use a cloud provider like Google Kubernetes Engine or Amazon Web Services to
create a Kubernetes cluster. This tutorial creates an
[external load balancer](/docs/tasks/access-application-cluster/create-external-load-balancer/),
which requires a cloud provider.
* Configure `kubectl` to communicate with your Kubernetes API server. For
instructions, see the documentation for your cloud provider.
{{% /capture %}}
{{% capture objectives %}}
* Run five instances of a Hello World application.
* Create a Service object that exposes an external IP address.
* Use the Service object to access the running application.
{{% /capture %}}
{{% capture lessoncontent %}}
## Creating a service for an application running in five pods
1. Run a Hello World application in your cluster:
kubectl run hello-world --replicas=5 --labels="run=load-balancer-example" --image=gcr.io/google-samples/node-hello:1.0 --port=8080
The preceding command creates a
[Deployment](/docs/concepts/workloads/controllers/deployment/)
object and an associated
[ReplicaSet](/docs/concepts/workloads/controllers/replicaset/)
object. The ReplicaSet has five
[Pods](/docs/concepts/workloads/pods/pod/),
each of which runs the Hello World application.
1. Display information about the Deployment:
kubectl get deployments hello-world
kubectl describe deployments hello-world
1. Display information about your ReplicaSet objects:
kubectl get replicasets
kubectl describe replicasets
1. Create a Service object that exposes the deployment:
kubectl expose deployment hello-world --type=LoadBalancer --name=my-service
1. Display information about the Service:
kubectl get services my-service
The output is similar to this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
my-service 10.3.245.137 104.198.205.71 8080/TCP 54s
Note: If the external IP address is shown as \<pending\>, wait for a minute
and enter the same command again.
1. Display detailed information about the Service:
kubectl describe services my-service
The output is similar to this:
Name: my-service
Namespace: default
Labels: run=load-balancer-example
Annotations: <none>
Selector: run=load-balancer-example
Type: LoadBalancer
IP: 10.3.245.137
LoadBalancer Ingress: 104.198.205.71
Port: <unset> 8080/TCP
NodePort: <unset> 32377/TCP
Endpoints: 10.0.0.6:8080,10.0.1.6:8080,10.0.1.7:8080 + 2 more...
Session Affinity: None
Events: <none>
Make a note of the external IP address (`LoadBalancer Ingress`) exposed by
your service. In this example, the external IP address is 104.198.205.71.
Also note the value of `Port` and `NodePort`. In this example, the `Port`
is 8080 and the `NodePort` is 32377.
1. In the preceding output, you can see that the service has several endpoints:
10.0.0.6:8080,10.0.1.6:8080,10.0.1.7:8080 + 2 more. These are internal
addresses of the pods that are running the Hello World application. To
verify these are pod addresses, enter this command:
kubectl get pods --output=wide
The output is similar to this:
NAME ... IP NODE
hello-world-2895499144-1jaz9 ... 10.0.1.6 gke-cluster-1-default-pool-e0b8d269-1afc
hello-world-2895499144-2e5uh ... 10.0.1.8 gke-cluster-1-default-pool-e0b8d269-1afc
hello-world-2895499144-9m4h1 ... 10.0.0.6 gke-cluster-1-default-pool-e0b8d269-5v7a
hello-world-2895499144-o4z13 ... 10.0.1.7 gke-cluster-1-default-pool-e0b8d269-1afc
hello-world-2895499144-segjf ... 10.0.2.5 gke-cluster-1-default-pool-e0b8d269-cpuc
1. Use the external IP address (`LoadBalancer Ingress`) to access the Hello
World application:
curl http://<external-ip>:<port>
where `<external-ip>` is the external IP address (`LoadBalancer Ingress`)
of your Service, and `<port>` is the value of `Port` in your Service
description.
If you are using minikube, typing `minikube service my-service` will
automatically open the Hello World application in a browser.
The response to a successful request is a hello message:
Hello Kubernetes!
{{% /capture %}}
{{% capture cleanup %}}
To delete the Service, enter this command:
kubectl delete services my-service
To delete the Deployment, the ReplicaSet, and the Pods that are running
the Hello World application, enter this command:
kubectl delete deployment hello-world
{{% /capture %}}
{{% capture whatsnext %}}
Learn more about
[connecting applications with services](/docs/concepts/services-networking/connect-applications-service/).
{{% /capture %}}
@@ -0,0 +1,304 @@
---
title: "Example: Deploying PHP Guestbook application with Redis"
reviewers:
- ahmetb
content_template: templates/tutorial
---
{{% capture overview %}}
This tutorial shows you how to build and deploy a simple, multi-tier web application using Kubernetes and [Docker](https://www.docker.com/). This example consists of the following components:
* A single-instance [Redis](https://redis.io/) master to store guestbook entries
* Multiple replicated Redis instances to serve reads
* Multiple web frontend instances
{{% /capture %}}
{{% capture objectives %}}
* Start up a Redis master.
* Start up Redis slaves.
* Start up the guestbook frontend.
* Expose and view the Frontend Service.
* Clean up.
{{% /capture %}}
{{% capture prerequisites %}}
{{< include "task-tutorial-prereqs.md" >}} {{< version-check >}}
Download the following configuration files:
1. [redis-master-deployment.yaml](/docs/tutorials/stateless-application/guestbook/redis-master-deployment.yaml)
1. [redis-master-service.yaml](/docs/tutorials/stateless-application/guestbook/redis-master-service.yaml)
1. [redis-slave-deployment.yaml](/docs/tutorials/stateless-application/guestbook/redis-slave-deployment.yaml)
1. [redis-slave-service.yaml](/docs/tutorials/stateless-application/guestbook/redis-slave-service.yaml)
1. [frontend-deployment.yaml](/docs/tutorials/stateless-application/guestbook/frontend-deployment.yaml)
1. [frontend-service.yaml](/docs/tutorials/stateless-application/guestbook/frontend-service.yaml)
{{% /capture %}}
{{% capture lessoncontent %}}
## Start up the Redis Master
The guestbook application uses Redis to store its data. It writes its data to a Redis master instance and reads data from multiple Redis slave instances.
### Creating the Redis Master Deployment
The manifest file, included below, specifies a Deployment controller that runs a single replica Redis master Pod.
1. Launch a terminal window in the directory you downloaded the manifest files.
2. Apply the Redis Master Deployment from the `redis-master-deployment.yaml` file:
kubectl apply -f redis-master-deployment.yaml
{{< code file="guestbook/redis-master-deployment.yaml" >}}
3. Query the list of Pods to verify that the Redis Master Pod is running:
kubectl get pods
The response should be similar to this:
NAME READY STATUS RESTARTS AGE
redis-master-1068406935-3lswp 1/1 Running 0 28s
4. Run the following command to view the logs from the Redis Master Pod:
kubectl logs -f POD-NAME
{{< note >}}
**Note:** Replace POD-NAME with the name of your Pod.
{{< /note >}}
### Creating the Redis Master Service
The guestbook applications needs to communicate to the Redis master to write its data. You need to apply a [Service](/docs/concepts/services-networking/service/) to proxy the traffic to the Redis master Pod. A Service defines a policy to access the Pods.
1. Apply the Redis Master Service from the following `redis-master-service.yaml` file:
kubectl apply -f redis-master-service.yaml
{{< code file="guestbook/redis-master-service.yaml" >}}
{{< note >}}
**Note:** This manifest file creates a Service named `redis-master` with a set of labels that match the labels previously defined, so the Service routes network traffic to the Redis master Pod.
{{< /note >}}
2. Query the list of Services to verify that the Redis Master Service is running:
kubectl get service
The response should be similar to this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes 10.0.0.1 <none> 443/TCP 1m
redis-master 10.0.0.151 <none> 6379/TCP 8s
## Start up the Redis Slaves
Although the Redis master is a single pod, you can make it highly available to meet traffic demands by adding replica Redis slaves.
### Creating the Redis Slave Deployment
Deployments scale based off of the configurations set in the manifest file. In this case, the Deployment object specifies two replicas.
If there are not any replicas running, this Deployment would start the two replicas on your container cluster. Conversely, if there are more than two replicas are running, it would scale down until two replicas are running.
1. Apply the Redis Slave Deployment from the `redis-slave-deployment.yaml` file:
kubectl apply -f redis-slave-deployment.yaml
{{< code file="guestbook/redis-slave-deployment.yaml" >}}
2. Query the list of Pods to verify that the Redis Slave Pods are running:
kubectl get pods
The response should be similar to this:
NAME READY STATUS RESTARTS AGE
redis-master-1068406935-3lswp 1/1 Running 0 1m
redis-slave-2005841000-fpvqc 0/1 ContainerCreating 0 6s
redis-slave-2005841000-phfv9 0/1 ContainerCreating 0 6s
### Creating the Redis Slave Service
The guestbook application needs to communicate to Redis slaves to read data. To make the Redis slaves discoverable, you need to set up a Service. A Service provides transparent load balancing to a set of Pods.
1. Apply the Redis Slave Service from the following `redis-slave-service.yaml` file:
kubectl apply -f redis-slave-service.yaml
{{< code file="guestbook/redis-slave-service.yaml" >}}
2. Query the list of Services to verify that the Redis Slave Service is running:
kubectl get services
The response should be similar to this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes 10.0.0.1 <none> 443/TCP 2m
redis-master 10.0.0.151 <none> 6379/TCP 1m
redis-slave 10.0.0.223 <none> 6379/TCP 6s
## Set up and Expose the Guestbook Frontend
The guestbook application has a web frontend serving the HTTP requests written in PHP. It is configured to connect to the `redis-master` Service for write requests and the `redis-slave` service for Read requests.
### Creating the Guestbook Frontend Deployment
1. Apply the frontend Deployment from the following `frontend-deployment.yaml` file:
kubectl apply -f frontend-deployment.yaml
{{< code file="guestbook/frontend-deployment.yaml" >}}
2. Query the list of Pods to verify that the three frontend replicas are running:
kubectl get pods -l app=guestbook -l tier=frontend
The response should be similar to this:
NAME READY STATUS RESTARTS AGE
frontend-3823415956-dsvc5 1/1 Running 0 54s
frontend-3823415956-k22zn 1/1 Running 0 54s
frontend-3823415956-w9gbt 1/1 Running 0 54s
### Creating the Frontend Service
The `redis-slave` and `redis-master` Services you applied are only accessible within the container cluster because the default type for a Service is [ClusterIP](/docs/concepts/services-networking/service/#publishing-services---service-types). `ClusterIP` provides a single IP address for the set of Pods the Service is pointing to. This IP address is accessible only within the cluster.
If you want guests to be able to access your guestbook, you must configure the frontend Service to be externally visible, so a client can request the Service from outside the container cluster. Minikube can only expose Services through `NodePort`.
{{< note >}}
**Note:** Some cloud providers, like Google Compute Engine or Google Kubernetes Engine, support external load balancers. If your cloud provider supports load balancers and you want to use it, simply delete or comment out `type: NodePort`, and uncomment `type: LoadBalancer`.
{{< /note >}}
1. Apply the frontend Service from the following `frontend-service.yaml` file:
kubectl apply -f frontend-service.yaml
{{< code file="guestbook/frontend-service.yaml" >}}
2. Query the list of Services to verify that the frontend Service is running:
kubectl get services
The response should be similar to this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
frontend 10.0.0.112 <none> 80:31323/TCP 6s
kubernetes 10.0.0.1 <none> 443/TCP 4m
redis-master 10.0.0.151 <none> 6379/TCP 2m
redis-slave 10.0.0.223 <none> 6379/TCP 1m
### Viewing the Frontend Service via `NodePort`
If you deployed this application to Minikube or a local cluster, you need to find the IP address to view your Guestbook.
1. Run the following command to get the IP address for the frontend Service.
minikube service frontend --url
The response should be similar to this:
http://192.168.99.100:31323
2. Copy the IP address, and load the page in your browser to view your guestbook.
### Viewing the Frontend Service via `LoadBalancer`
If you deployed the `frontend-service.yaml` manifest with type: `LoadBalancer` you need to find the IP address to view your Guestbook.
1. Run the following command to get the IP address for the frontend Service.
kubectl get service frontend
The response should be similar to this:
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
frontend 10.51.242.136 109.197.92.229 80:32372/TCP 1m
2. Copy the External IP address, and load the page in your browser to view your guestbook.
## Scale the Web Frontend
Scaling up or down is easy because your servers are defined as a Service that uses a Deployment controller.
1. Run the following command to scale up the number of frontend Pods:
kubectl scale deployment frontend --replicas=5
2. Query the list of Pods to verify the number of frontend Pods running:
kubectl get pods
The response should look similar to this:
NAME READY STATUS RESTARTS AGE
frontend-3823415956-70qj5 1/1 Running 0 5s
frontend-3823415956-dsvc5 1/1 Running 0 54m
frontend-3823415956-k22zn 1/1 Running 0 54m
frontend-3823415956-w9gbt 1/1 Running 0 54m
frontend-3823415956-x2pld 1/1 Running 0 5s
redis-master-1068406935-3lswp 1/1 Running 0 56m
redis-slave-2005841000-fpvqc 1/1 Running 0 55m
redis-slave-2005841000-phfv9 1/1 Running 0 55m
3. Run the following command to scale down the number of frontend Pods:
kubectl scale deployment frontend --replicas=2
4. Query the list of Pods to verify the number of frontend Pods running:
kubectl get pods
The response should look similar to this:
NAME READY STATUS RESTARTS AGE
frontend-3823415956-k22zn 1/1 Running 0 1h
frontend-3823415956-w9gbt 1/1 Running 0 1h
redis-master-1068406935-3lswp 1/1 Running 0 1h
redis-slave-2005841000-fpvqc 1/1 Running 0 1h
redis-slave-2005841000-phfv9 1/1 Running 0 1h
{{% /capture %}}
{{% capture cleanup %}}
Deleting the Deployments and Services also deletes any running Pods. Use labels to delete multiple resources with one command.
1. Run the following commands to delete all Pods, Deployments, and Services.
kubectl delete deployment -l app=redis
kubectl delete service -l app=redis
kubectl delete deployment -l app=guestbook
kubectl delete service -l app=guestbook
The responses should be:
deployment "redis-master" deleted
deployment "redis-slave" deleted
service "redis-master" deleted
service "redis-slave" deleted
deployment "frontend" deleted
service "frontend" deleted
2. Query the list of Pods to verify that no Pods are running:
kubectl get pods
The response should be this:
No resources found.
{{% /capture %}}
{{% capture whatsnext %}}
* Complete the [Kubernetes Basics](/docs/tutorials/kubernetes-basics/) Interactive Tutorials
* Use Kubernetes to create a blog using [Persistent Volumes for MySQL and Wordpress](/docs/tutorials/stateful-application/mysql-wordpress-persistent-volume/#visit-your-new-wordpress-blog)
* Read more about [connecting applications](/docs/concepts/services-networking/connect-applications-service/)
* Read more about [Managing Resources](/docs/concepts/cluster-administration/manage-deployment/#using-labels-effectively)
{{% /capture %}}
@@ -0,0 +1,36 @@
apiVersion: apps/v1 # for versions before 1.9.0 use apps/v1beta2
kind: Deployment
metadata:
name: frontend
spec:
selector:
matchLabels:
app: guestbook
tier: frontend
replicas: 3
template:
metadata:
labels:
app: guestbook
tier: frontend
spec:
containers:
- name: php-redis
image: gcr.io/google-samples/gb-frontend:v4
resources:
requests:
cpu: 100m
memory: 100Mi
env:
- name: GET_HOSTS_FROM
value: dns
# Using `GET_HOSTS_FROM=dns` requires your cluster to
# provide a dns service. As of Kubernetes 1.3, DNS is a built-in
# service launched automatically. However, if the cluster you are using
# does not have a built-in DNS service, you can instead
# access an environment variable to find the master
# service's host. To do so, comment out the 'value: dns' line above, and
# uncomment the line below:
# value: env
ports:
- containerPort: 80
@@ -0,0 +1,18 @@
apiVersion: v1
kind: Service
metadata:
name: frontend
labels:
app: guestbook
tier: frontend
spec:
# comment or delete the following line if you want to use a LoadBalancer
type: NodePort
# if your cluster supports it, uncomment the following to automatically create
# an external load-balanced IP for the frontend service.
# type: LoadBalancer
ports:
- port: 80
selector:
app: guestbook
tier: frontend
@@ -0,0 +1,27 @@
apiVersion: apps/v1 # for versions before 1.9.0 use apps/v1beta2
kind: Deployment
metadata:
name: redis-master
spec:
selector:
matchLabels:
app: redis
role: master
tier: backend
replicas: 1
template:
metadata:
labels:
app: redis
role: master
tier: backend
spec:
containers:
- name: master
image: k8s.gcr.io/redis:e2e # or just image: redis
resources:
requests:
cpu: 100m
memory: 100Mi
ports:
- containerPort: 6379
@@ -0,0 +1,16 @@
apiVersion: v1
kind: Service
metadata:
name: redis-master
labels:
app: redis
role: master
tier: backend
spec:
ports:
- port: 6379
targetPort: 6379
selector:
app: redis
role: master
tier: backend
@@ -0,0 +1,38 @@
apiVersion: apps/v1 # for versions before 1.9.0 use apps/v1beta2
kind: Deployment
metadata:
name: redis-slave
spec:
selector:
matchLabels:
app: redis
role: slave
tier: backend
replicas: 2
template:
metadata:
labels:
app: redis
role: slave
tier: backend
spec:
containers:
- name: slave
image: gcr.io/google_samples/gb-redisslave:v1
resources:
requests:
cpu: 100m
memory: 100Mi
env:
- name: GET_HOSTS_FROM
value: dns
# Using `GET_HOSTS_FROM=dns` requires your cluster to
# provide a dns service. As of Kubernetes 1.3, DNS is a built-in
# service launched automatically. However, if the cluster you are using
# does not have a built-in DNS service, you can instead
# access an environment variable to find the master
# service's host. To do so, comment out the 'value: dns' line above, and
# uncomment the line below:
# value: env
ports:
- containerPort: 6379
@@ -0,0 +1,15 @@
apiVersion: v1
kind: Service
metadata:
name: redis-slave
labels:
app: redis
role: slave
tier: backend
spec:
ports:
- port: 6379
selector:
app: redis
role: slave
tier: backend
@@ -0,0 +1,427 @@
---
title: Hello Minikube
content_template: templates/tutorial
---
{{% capture overview %}}
The goal of this tutorial is for you to turn a simple Hello World Node.js app
into an application running on Kubernetes. The tutorial shows you how to
take code that you have developed on your machine, turn it into a Docker
container image and then run that image on [Minikube](/docs/getting-started-guides/minikube).
Minikube provides a simple way of running Kubernetes on your local machine for free.
{{% /capture %}}
{{% capture objectives %}}
* Run a hello world Node.js application.
* Deploy the application to Minikube.
* View application logs.
* Update the application image.
{{% /capture %}}
{{% capture prerequisites %}}
* For OS X, you need [Homebrew](https://brew.sh) to install the `xhyve`
driver.
* [NodeJS](https://nodejs.org/en/) is required to run the sample application.
* Install Docker. On OS X, we recommend
[Docker for Mac](https://docs.docker.com/engine/installation/mac/).
{{% /capture %}}
{{% capture lessoncontent %}}
## Create a Minikube cluster
This tutorial uses [Minikube](https://github.com/kubernetes/minikube) to
create a local cluster. This tutorial also assumes you are using
[Docker for Mac](https://docs.docker.com/engine/installation/mac/)
on OS X. If you are on a different platform like Linux, or using VirtualBox
instead of Docker for Mac, the instructions to install Minikube may be
slightly different. For general Minikube installation instructions, see
the [Minikube installation guide](/docs/getting-started-guides/minikube/).
Use `curl` to download and install the latest Minikube release:
```shell
curl -Lo minikube https://storage.googleapis.com/minikube/releases/latest/minikube-darwin-amd64 && \
chmod +x minikube && \
sudo mv minikube /usr/local/bin/
```
Use Homebrew to install the xhyve driver and set its permissions:
```shell
brew install docker-machine-driver-xhyve
sudo chown root:wheel $(brew --prefix)/opt/docker-machine-driver-xhyve/bin/docker-machine-driver-xhyve
sudo chmod u+s $(brew --prefix)/opt/docker-machine-driver-xhyve/bin/docker-machine-driver-xhyve
```
Use Homebrew to download the `kubectl` command-line tool, which you can
use to interact with Kubernetes clusters:
```shell
brew install kubectl
```
Determine whether you can access sites like [https://cloud.google.com/container-registry/](https://cloud.google.com/container-registry/) directly without a proxy, by opening a new terminal and using
```shell
curl --proxy "" https://cloud.google.com/container-registry/
```
Make sure that the Docker daemon is started. You can determine if docker is running by using a command such as:
```shell
docker images
```
If NO proxy is required, start the Minikube cluster:
```shell
minikube start --vm-driver=xhyve
```
If a proxy server is required, use the following method to start Minikube cluster with proxy setting:
```shell
minikube start --vm-driver=xhyve --docker-env HTTP_PROXY=http://your-http-proxy-host:your-http-proxy-port --docker-env HTTPS_PROXY=http(s)://your-https-proxy-host:your-https-proxy-port
```
The `--vm-driver=xhyve` flag specifies that you are using Docker for Mac. The
default VM driver is VirtualBox.
Note if `minikube start --vm-driver=xhyve` is unsuccessful due to the error:
```
Error creating machine: Error in driver during machine creation: Could not convert the UUID to MAC address: exit status 1
```
Then the following may resolve the `minikube start --vm-driver=xhyve` issue:
```
rm -rf ~/.minikube
sudo chown root:wheel $(brew --prefix)/opt/docker-machine-driver-xhyve/bin/docker-machine-driver-xhyve
sudo chmod u+s $(brew --prefix)/opt/docker-machine-driver-xhyve/bin/docker-machine-driver-xhyve
```
Now set the Minikube context. The context is what determines which cluster
`kubectl` is interacting with. You can see all your available contexts in the
`~/.kube/config` file.
```shell
kubectl config use-context minikube
```
Verify that `kubectl` is configured to communicate with your cluster:
```shell
kubectl cluster-info
```
Open the Kubernetes dashboard in a browser:
```shell
minikube dashboard
```
## Create your Node.js application
The next step is to write the application. Save this code in a folder named `hellonode`
with the filename `server.js`:
{{< code language="js" file="server.js" >}}
Run your application:
```shell
node server.js
```
You should be able to see your "Hello World!" message at http://localhost:8080/.
Stop the running Node.js server by pressing **Ctrl-C**.
The next step is to package your application in a Docker container.
## Create a Docker container image
Create a file, also in the `hellonode` folder, named `Dockerfile`. A Dockerfile describes
the image that you want to build. You can build a Docker container image by extending an
existing image. The image in this tutorial extends an existing Node.js image.
{{< code language="conf" file="Dockerfile" >}}
This recipe for the Docker image starts from the official Node.js LTS image
found in the Docker registry, exposes port 8080, copies your `server.js` file
to the image and starts the Node.js server.
Because this tutorial uses Minikube, instead of pushing your Docker image to a
registry, you can simply build the image using the same Docker host as
the Minikube VM, so that the images are automatically present. To do so, make
sure you are using the Minikube Docker daemon:
```shell
eval $(minikube docker-env)
```
**Note:** Later, when you no longer wish to use the Minikube host, you can undo
this change by running `eval $(minikube docker-env -u)`.
Build your Docker image, using the Minikube Docker daemon (mind the trailing dot):
```shell
docker build -t hello-node:v1 .
```
Now the Minikube VM can run the image you built.
## Create a Deployment
A Kubernetes [*Pod*](/docs/concepts/workloads/pods/pod/) is a group of one or more Containers,
tied together for the purposes of administration and networking. The Pod in this
tutorial has only one Container. A Kubernetes
[*Deployment*](/docs/concepts/workloads/controllers/deployment/) checks on the health of your
Pod and restarts the Pod's Container if it terminates. Deployments are the
recommended way to manage the creation and scaling of Pods.
Use the `kubectl run` command to create a Deployment that manages a Pod. The
Pod runs a Container based on your `hello-node:v1` Docker image:
```shell
kubectl run hello-node --image=hello-node:v1 --port=8080
```
View the Deployment:
```shell
kubectl get deployments
```
Output:
```shell
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE
hello-node 1 1 1 1 3m
```
View the Pod:
```shell
kubectl get pods
```
Output:
```shell
NAME READY STATUS RESTARTS AGE
hello-node-714049816-ztzrb 1/1 Running 0 6m
```
View cluster events:
```shell
kubectl get events
```
View the `kubectl` configuration:
```shell
kubectl config view
```
For more information about `kubectl`commands, see the
[kubectl overview](/docs/user-guide/kubectl-overview/).
## Create a Service
By default, the Pod is only accessible by its internal IP address within the
Kubernetes cluster. To make the `hello-node` Container accessible from outside the
Kubernetes virtual network, you have to expose the Pod as a
Kubernetes [*Service*](/docs/concepts/services-networking/service/).
From your development machine, you can expose the Pod to the public internet
using the `kubectl expose` command:
```shell
kubectl expose deployment hello-node --type=LoadBalancer
```
View the Service you just created:
```shell
kubectl get services
```
Output:
```shell
NAME CLUSTER-IP EXTERNAL-IP PORT(S) AGE
hello-node 10.0.0.71 <pending> 8080/TCP 6m
kubernetes 10.0.0.1 <none> 443/TCP 14d
```
The `--type=LoadBalancer` flag indicates that you want to expose your Service
outside of the cluster. On cloud providers that support load balancers,
an external IP address would be provisioned to access the Service. On Minikube,
the `LoadBalancer` type makes the Service accessible through the `minikube service`
command.
```shell
minikube service hello-node
```
This automatically opens up a browser window using a local IP address that
serves your app and shows the "Hello World" message.
Assuming you've sent requests to your new web service using the browser or curl,
you should now be able to see some logs:
```shell
kubectl logs <POD-NAME>
```
## Update your app
Edit your `server.js` file to return a new message:
```javascript
response.end('Hello World Again!');
```
Build a new version of your image (mind the trailing dot):
```shell
docker build -t hello-node:v2 .
```
Update the image of your Deployment:
```shell
kubectl set image deployment/hello-node hello-node=hello-node:v2
```
Run your app again to view the new message:
```shell
minikube service hello-node
```
## Enable addons
Minikube has a set of built-in addons that can be enabled, disabled and opened in the local Kubernetes environment.
First list the currently supported addons:
```shell
minikube addons list
```
Output:
```shell
- storage-provisioner: enabled
- kube-dns: enabled
- registry: disabled
- registry-creds: disabled
- addon-manager: enabled
- dashboard: disabled
- default-storageclass: enabled
- coredns: disabled
- heapster: disabled
- efk: disabled
- ingress: disabled
```
Minikube must be running for these commands to take effect. To enable `heapster` addon, for example:
```shell
minikube addons enable heapster
```
Output:
```shell
heapster was successfully enabled
```
View the Pod and Service you just created:
```shell
kubectl get po,svc -n kube-system
```
Output:
```shell
NAME READY STATUS RESTARTS AGE
po/heapster-zbwzv 1/1 Running 0 2m
po/influxdb-grafana-gtht9 2/2 Running 0 2m
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
svc/heapster NodePort 10.0.0.52 <none> 80:31655/TCP 2m
svc/monitoring-grafana NodePort 10.0.0.33 <none> 80:30002/TCP 2m
svc/monitoring-influxdb ClusterIP 10.0.0.43 <none> 8083/TCP,8086/TCP 2m
```
Open the endpoint to interacting with heapster in a browser:
```shell
minikube addons open heapster
```
Output:
```shell
Opening kubernetes service kube-system/monitoring-grafana in default browser...
```
## Clean up
Now you can clean up the resources you created in your cluster:
```shell
kubectl delete service hello-node
kubectl delete deployment hello-node
```
Optionally, force removal of the Docker images created:
```shell
docker rmi hello-node:v1 hello-node:v2 -f
```
Optionally, stop the Minikube VM:
```shell
minikube stop
eval $(minikube docker-env -u)
```
Optionally, delete the Minikube VM:
```shell
minikube delete
```
{{% /capture %}}
{{% capture whatsnext %}}
* Learn more about [Deployment objects](/docs/concepts/workloads/controllers/deployment/).
* Learn more about [Deploying applications](/docs/user-guide/deploying-applications/).
* Learn more about [Service objects](/docs/concepts/services-networking/service/).
{{% /capture %}}
@@ -0,0 +1,9 @@
var http = require('http');
var handleRequest = function(request, response) {
console.log('Received request for URL: ' + request.url);
response.writeHead(200);
response.end('Hello World!');
};
var www = http.createServer(handleRequest);
www.listen(8080);