Knative Serving

Knative consists of two main components:

  • Knative Serving

  • Knative Eventing

Knative Serving, which is covered in this section, takes care of deploying and running containerized applications on Kubernetes. Developers use Knative Serving to deploy and run their applications without having to deal with cluster or server management. This is known as the serverless model.

The serverless model can help you focus on writing code and creating new features, and reduce the time and effort dedicated to operational tasks. Knative Serving handles tasks such as traffic routing, revision control, and pod autoscaling for you.

Services

The primary entity in Knative Serving is the Service. You can think of a Knative service as a deployed application. To represent this entity, the serving.knative.dev API provides the Service object as a Kubernetes custom resource.

Knative Service objects define how Knative manages the application life cycle, and how Kubernetes runs the application. This resource specifies the configuration parameters required to deploy a serverless application, such as the container image or the port.

Note

Do not confuse Knative services (Service.serving.knative.dev) with regular Kubernetes Service resources. They are different objects.

You can create a new Knative service from any container image that exposes a network port. To create a new service, you can either write the service definition in a YAML file and apply the file, or you can use the kn service create command, as the following example demonstrates:

kn service create echo --image=quay.io/redhattraining/kbe-knative-echo:v1 --port=8080

The preceding command creates a new Knative service called echo, from the quay.io/redhattraining/kbe-knative-echo:v1 image. The newly created service deploys the specified image in a pod that listens on port 8080.

When you create a Knative service, Knative also creates a revision and a route.

Revisions

When you create a Knative service, Knative creates a Revision tied to the service. Revisions are how Knative keeps control of different versions of a Knative service. Knative also creates a new revision when you update a service, if necessary.

The Revision custom resource is also included in the serving.knative.dev API, and represents a specific version of your application.

You can list the revisions of a given service with the kn revision list command. For example, you can get the revisions of the echo service by using the -s parameter to filter by service:

kn revisions list -s echo

The output should be similar to the following:

NAME         SERVICE   TRAFFIC   TAGS   GENERATION   AGE    CONDITIONS   READY   REASON
echo-00001   echo                       1            80s    4 OK / 4     True

You can also inspect a specific revision with the kn revision describe command. The following example prints a description of the first revision of the echo service.

kn revision describe echo-00001
Name:       echo-00001
Namespace:  default
Age:        16m
Image:      quay.io/redhattraining/kbe-knative-echo:v1 (pinned to 5d99aa)
Replicas:   1/1
Port:       8080
Service:    echo

Conditions:
  OK TYPE                  AGE REASON
  ++ Ready                 10m
  ++ ContainerHealthy      10m
  ++ ResourcesAvailable    10m
  ++ Active                56s

The OK column can show different states for each condition.

  • ++: The condition passes.

  • I: The condition does not pass. The reason column shows an informational message.

  • !!: An error or another unexpected event happened.

  • ??: Knative does not have information about the condition.

Each Revision object owns a regular kubernetes Deployment object, and therefore, the pods associated to the deployment. If you create a new revision, then Knative creates a new deployment associated to the new revision.

Autoscaling

By default, Knative automatically adjusts the number of replicas of a service based on the traffic load. If you stop sending traffic to the service, then, after some time, Knative scales down the service and marks the revisions as not active.

You can verify this behavior by inspecting the Active condition of the revision:

kn revision describe echo-00001
Name:       echo-00001
Namespace:  default
Age:        2m
Image:      quay.io/redhattraining/kbe-knative-echo:v1 (pinned to 5d99aa)
Replicas:   0/0
Port:       8080
Service:    echo

Conditions:
  OK TYPE                  AGE REASON
  ++ Ready                  2m
  ++ ContainerHealthy       2m
  ++ ResourcesAvailable     2m
   I Active                 1m NoTraffic

You can also verify that no pods are running after Knative scales down the service:

kubectl get pods
No resources found in default namespace.

If you send a request to your service, then Knative marks the revision as active, scales up the service and creates a new pod to handle the request.

kn revision describe echo-00001
Name:       echo-00001
Namespace:  default
Age:        16m
Image:      quay.io/redhattraining/kbe-knative-echo:v1 (pinned to 5d99aa)
Replicas:   1/1
Port:       8080
Service:    echo

Conditions:
  OK TYPE                  AGE REASON
  ++ Ready                 16m
  ++ ContainerHealthy      16m
  ++ ResourcesAvailable    16m
  ++ Active                18s

Note that the revision has been ready, healthy, and available for 16 minutes, but active only for the last 18 seconds.

Routes

When you create a Knative service, Knative also creates a route. You can inspect the route associated with a Knative service. In Knative, a route maps traffic between a URL and one or more revisions.

Similar to services and revisions, you can list routes.

kn routes list

Likewise, you can inspect a single route.

kn routes describe echo
Name:       echo
Namespace:  default
Age:        18m
URL:        http://echo.default.10.106.211.36.sslip.io
Service:    echo

Traffic Targets:
  100%  @latest (echo-00001)

Conditions:
  OK TYPE                      AGE REASON
  ++ Ready                     18m
  ++ AllTrafficAssigned        18m
  ++ CertificateProvisioned    18m TLSNotEnabled
  ++ IngressReady              18m

A Knative route can target one or more revisions. In this particular example, the route sends all traffic to the echo-00001 revision.

Note

You can also use kubectl to inspect Knative custom resources, such as services, revisions, and routes.

Updating a Knative Service

Use the kn service update command to update a Knative service. Alternatively, you can patch the Knative Service object or apply a YAML file to trigger an update.

The following example updates the echo service with a new version of the container image.

kn service update echo --image=quay.io/redhattraining/kbe-knative-echo:v2
Updating Service 'echo' in namespace 'default':

  0.017s The Configuration is still working to reflect the latest desired specification.
  6.915s Traffic is not yet migrated to the latest revision.
  6.995s Ingress has not yet been reconciled.
  7.005s Waiting for load balancer to be ready
  7.133s Ready to serve.

Service 'echo' updated to latest revision 'echo-00002' is available at URL:
http://echo.default.10.106.211.36.sslip.io

If the update includes changes in the application source, such as a new version of the container image, then Knative creates a new revision. In this case, Knative has created the echo-00002 revision.

kn revisions list
NAME         SERVICE   TRAFFIC   TAGS   GENERATION   AGE     CONDITIONS   READY
echo-00002   echo      100%             2            99s     4 OK / 4     True
echo-00001   echo                       1            26m     3 OK / 4     True

Updating the service also updates the route. In this example, Knative adjusts the route to send traffic to the latest echo-00002 revision.

kn routes describe echo
Name:       echo
Namespace:  default
Age:        26m
URL:        http://echo.default.10.106.211.36.sslip.io
Service:    echo

Traffic Targets:
  100%  @latest (echo-00002)

Conditions:
  OK TYPE                      AGE REASON
  ++ Ready                      1m
  ++ AllTrafficAssigned        26m
  ++ CertificateProvisioned    26m TLSNotEnabled
  ++ IngressReady               1m