4.1 kubectl Basics

The kubectl utility is a command line tool that interfaces with the API Server to run commands against the cluster. The tool is typically run on the master node of the cluster. It effectively grants full administrative rights to the cluster and all of the nodes in the cluster.

The kubectl utility is documented fully at:

https://kubernetes.io/docs/user-guide/kubectl-overview/

In this section, we describe basic usage of the tool to get you started creating and managing pods and services within your environment.

Get information about the nodes in your cluster

To simply obtain a listing of all of the nodes within a cluster and the status of each node, use the kubectl get command. This command can be used to obtain listings of any kind of resource that Kubernetes supports. In this case, we are interested in the nodes resource:

# kubectl get nodes
NAME                STATUS    ROLES   AGE       VERSION
test1.example.com   Ready     master  1h        v1.8.4+2.0.1.el7
test2.example.com   Ready     <none>  1h        v1.8.4+2.0.1.el7
test3.example.com   Ready     <none>  1h        v1.8.4+2.0.1.el7

You can get more detailed information about any resource using the kubectl describe command. If you specify the name of the resource, the output is limited to information about that resource alone, otherwise full details of all resources are also printed to screen:

# kubectl describe nodes test3.example.com
Name:                   test3.example.com
Role:
Labels:                 beta.kubernetes.io/arch=amd64
                        beta.kubernetes.io/os=linux
                        kubernetes.io/hostname=test3.example.com
Annotations:            flannel.alpha.coreos.com/backend-data={"VtepMAC":"02:e6:df:13:b1:eb"}
                        flannel.alpha.coreos.com/backend-type=vxlan
                        flannel.alpha.coreos.com/kube-subnet-manager=true
                        flannel.alpha.coreos.com/public-ip=198.51.100.13
                        node.alpha.kubernetes.io/ttl=0
                        volumes.kubernetes.io/controller-managed-attach-detach=true
...

Run an application in a pod

To create a pod with a single running Docker container, you can use the kubectl run command. For example:

# kubectl run hello-world --image=nginxdemos/hello --port=80
deployment "hello-world" created

Substitute hello-world with a name for your deployment. Your pods are named using the deployment name as a prefix. Substitute nginxdemos/hello with a Docker image that can be pulled by the Docker engine. Substitute the port 80 with whatever port is used to provide network access to your application.

Tip

Deployment, pod and service names conform to a requirement to match a DNS-1123 label. These must consist of lower case alphanumeric characters or '-', and must start and end with an alphanumeric character. The regular expression used to validate names is '[a-z0-9]([-a-z0-9]*[a-z0-9])?'. If you use a name, for your deployment, that does not validate, an error is returned.

There are many additional optional parameters that can be used when you run a new application within Kubernetes. For instance, at run time, you can specify how many replica pods should be started, or you might apply a label to the deployment to make it easier to identify pod components. To see a full list of options available to you, run kubectl run -h.

Check that your new application deployment has created one or more pods, using kubectl get pods:

# kubectl get pods
NAME                          READY     STATUS    RESTARTS   AGE
hello-world-178523330-61d6n   1/1       Running   0          1m

Use kubectl describe to show a more detailed view of your pods, including which containers are running and what image they are based on, as well as which node is currently hosting the pod:

# kubectl describe pods
Name:           hello-world-178523330-61d6n
Namespace:      default
Node:           test3.example.com/10.147.25.197
Start Time:     Tue, 27 Jun 2017 03:30:36 -0700
Labels:         pod-template-hash=178523330
                run=hello-world
Annotations:    kubernetes.io/created-by={"kind":"SerializedReference","apiVersion":"v1",
                "reference":{"kind":"ReplicaSet","namespace":"default","name":"hello-world-178523330",
                "uid":"a8167abe-5b23-11e7-aa6e-0800276095d5","a...
Status:         Running
IP:             10.244.2.2
Controllers:    ReplicaSet/hello-world-178523330
Containers:
  hello-world:
    Container ID:       docker://a4773781ca120107a13d633ced35ad734254f61684e25d287e74cfc678aec657
    Image:              nginxdemos/hello
    Image ID:           docker-pullable://nginxdemos/hello@sha256:e2c04f58cdc4a1cdf269226a6091...
    Port:               80/TCP
    State:              Running
      Started:          Tue, 27 Jun 2017 03:30:43 -0700
    Ready:              True
    Restart Count:      0
    Environment:        <none>
    Mounts:
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-vn6kf (ro)
Conditions:
  Type          Status
  Initialized   True 
  Ready         True 
  PodScheduled  True 
Volumes:
  default-token-vn6kf:
    Type:       Secret (a volume populated by a Secret)
    SecretName: default-token-vn6kf
    Optional:   false
QoS Class:      BestEffort
Node-Selectors: <none>
Tolerations:    node.alpha.kubernetes.io/notReady=:Exists:NoExecute for 300s
                node.alpha.kubernetes.io/unreachable=:Exists:NoExecute for 300s
Events:
...

Scale a pod deployment

To change the number of instances of the same pod that you are running, you can use the kubectl scale deployment command. For example:

# kubectl scale deployment hello-world --replicas=3
deployment "hello-world" scaled

You can check that the number of pod instances has been scaled appropriately:

# kubectl get pods
NAME                          READY     STATUS    RESTARTS   AGE
hello-world-178523330-0cjk4   1/1       Running   0          18s
hello-world-178523330-61d6n   1/1       Running   0          26m
hello-world-178523330-dzmtd   1/1       Running   0          18s

Expose a service object for your application

Typically, while many applications may only need to communicate internally within a pod, or even across pods, you may need to expose your application externally so that clients outside of the Kubernetes cluster can interface with the application. This is done by creating a service definition for the deployment.

To expose a deployment using a service object, you must define the service type that should be used. If you are not using a cloud-based load balancing service, you can set the service type to NodePort. The NodePort service exposes the application running within the cluster on a dedicated port on the public IP address on all of the nodes within the cluster. Use the kubectl expose deployment to create a new service.

# kubectl expose deployment hello-world --type=NodePort --name=hello-service
service "hello-service" exposed

Use kubectl get services to list the different services that the cluster is running, and to obtain the port information required to access the service:

# kubectl get services hello-service
NAME            CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE
hello-service   10.110.35.88   <nodes>       80:32164/TCP   18m

In this example output, you can see that traffic to port 80 inside the cluster is mapped to the NodePort 32164. The external IP that can be used to access the service is listed as <nodes>, meaning that if you connect to the external IP address for any of the nodes within the cluster on the port 32164, you are able access the service.

For the sake of the example in this guide, you can open a web browser to point at any of the nodes in the cluster, such as http://test3.example.com:32164/, and it should display the NGINX demonstration application.

Delete a service or deployment

Objects can be deleted easily within Kubernetes so that your environment can be cleaned. Use the kubectl delete command to remove an object.

To delete a service, specify the services object and the name of the service that you wish to remove:

# kubectl delete services hello-service

To delete an entire deployment, and all of the pod replicas running for that deployment, specify the deployment object and the name that you used to create the deployment:

# kubectl delete deployment hello-world

Work with namespaces

Namespaces can be used to further separate resource usage and to provide limited environments for particular use cases. By default, Kubernetes configures a namespace for Kubernetes system components and a standard namespace to be used for all other deployments for which no namespace is defined.

To view existing namespaces, use the kubectl get namespaces and kubectl describe namespaces commands.

kubectl only displays resources in the default namespace, unless you set the namespace specifically for a request. Therefore, if you need to view the pods specific to the Kubernetes system, you would use the --namespace option to set the namespace to kube-system for the request. For example:

# kubectl get pods --namespace=kube-system
NAME                                         READY     STATUS    RESTARTS   AGE
etcd-master.example.com                      1/1       Running   0          2d
kube-apiserver-master.example.com            1/1       Running   0          2d
kube-controller-manager-master.example.com   1/1       Running   0          2d
kube-dns-978711586-lhlvs                     3/3       Running   0          2d
kube-flannel-ds-5cs4b                        2/2       Running   1          2d
kube-flannel-ds-ms3ms                        2/2       Running   0          2d
kube-flannel-ds-wjtjg                        2/2       Running   2          2d
kube-proxy-6qw0f                             1/1       Running   0          2d
kube-proxy-v18xk                             1/1       Running   0          2d
kube-proxy-zqg5b                             1/1       Running   0          2d
kube-scheduler-master.example.com            1/1       Running   0          2d