Services

Service is a kubernetes object that enables various communication between various components within and outside of the application.
Kubernetes services helps us to connect applications together with other applications or users.

For example, our application has group of PODs running various sections such as a group for serving front-end load to users, other for running backend processes and third one connecting to external data source.
It is services that enable connectivity between these groups of PODs.
Services enable the front end application to be made available to users, it helps communication between backend and front end parts and helps in establishing connectivity to an external datasource.
Thus services enable loose coupling between microservices in our application.

Service Types

  • NodePort
    This service makes internal POD accessible on a port on the node.
  • ClusterIP This service creates a vitrualIP inside the cluster, to enable communication between different services such as set of frontend servers to a set of backend servers.
  • LoadBalancer This provisions a load balancer for our application in supported cloud providers.

Create a service -- Nodeport

service-definition.yaml

apiVersion: v1
kind: Service
metadata:
  name: myapp-service
spec:
  type: NodePort
  ports:
    - targetPort: 80
      port: 80
      nodePort: 30008
  # service should be linked to a POD inorder to access
  selector: 
  # to select a POD, below are POD labels
    app: myapp
    type: front-end

Among ports, port is only one which is mandatory. If we dont provide target port, by default target port is assumed to be same as port. If we dont provide nodePort, the free port between range 30000-32767 will be assigned as nodeport.

kubectl create -f <service-definition file>
To create a service

kubectl get services
To view the list of services.

Now we can access the POD using curl
curl http://192.168.1.2:30008
Here 192.168.1.2 is the IP address of node and 30008 is the nodeport.

minikube service <servicename> --url
To get the url of that specific service.

Create a service -- ClusterIP

A full stack application will have different types of PODs hosting different parts of an application.
To connect different pods like frontend pods with backend pods and backend pods with database pods.
All pods are assigned with a specific IP address, but IP addresses are not static because these PODS may go at anytime and new PODS may come into action, so we cannot rely on IP addresses for internal communication between the application.
A kubernetes service can help group the PODs together and provide single interface to access the PODs in a group. The request will be forwarded to one of the PODs under the service randomly.
In this case, two services will be created one for backend and one for redis for commnication.
This enables us to easily and effectively deploy microservices based application on kubernetes cluster. Each layer can scale or move without effecting various services. Each service gets an IP and name and assigned to it inside the cluster and that it is name that to be used by other PODs to access the service. This type of service is called clusterIP.

service-definition.yaml

apiVersion: v1
kind: Service
metadata:
  name: back-end
spec:
  type: ClusterIP
  # ClusterIP is the default service
  ports:
    - targetPort: 80
      port: 80
  selector: 
  # to select a POD, below are POD labels
    app: myapp
    type: back-end

Create a service -- LoadBalancer

To make the application accessible to the external user, we create the services of type NodePort. The services of type NodePort helps in receiving the traffic on the ports of the node and routing the traffic to the respective PODs.
When we have 4 nodes, with what url we can access the application, we can access the application with any of the 4 urls(IP address of the nodes:port).
All the PODs of the cluster can be accessed from any node of the cluster (irrespective of the particular node in which they reside).
The end users want a single url(not many) to access, to achieve that we can create a new VM for load balancing purpose and install and configure a suitable loadbalancer on it (like proxy) and then configure the load balancer to route traffic to the underlying nodes. This way will be tedious.
If we were on a supported cloud platform like Google Cloud or NWS or Azure, we could leverage the native load balancer of that cloud platform. Kubernetes has support for integrating with the native load balancers of certain cloud providers and configuring that for us.

For this, we just need to set the type as LoadBalancer.

service-definition.yaml

apiVersion: v1
kind: Service
metadata:
  name: myapp-service
spec:
  type: LoadBalancer
  ports:
    - targetPort: 80
      port: 80
      nodePort: 30008
  selector: 
    app: myapp
    type: front-end

This will work only on cloud platforms.