Why does K8s abandon Docker

Why does K8s abandon Docker

In the process of learning container technology recently, I saw something about Kubernetes "abandoning Docker", and I was worried about whether learning Docker is still valuable now, and whether I should switch to containerd or other runtimes now.
With a deeper understanding, these doubts do have some truth. Three years ago, when Kubernetes released the news to "abandon Docker", it really caused a "uproar" in the Kubernetes community, and the impact even spread outside the community, which also caused Kubernetes to write several blogs to repeat Explain why you did this. Three years have passed, and although Kubernetes 1.24 has achieved the goal of "deprecation", there is still no clear understanding of this matter, so record the whole story of this incident.

Background: The evolution of Kubernetes

To understand why K8s "abandoned Docker", we have to review the history of K8s development.

Kubernetes is an open source container infrastructure orchestration framework released by Google as early as 2014. This technology has a theoretical basis, namely: Borg. Borg is a part of Google's entire infrastructure system. Borg is a part of Google's entire infrastructure system. Google has also published a number of papers on Borg as its theoretical support. It carries many leading technologies in the industry such as MapReduce and BigTable. Therefore, the Borg system has always been hailed as the most powerful "secret weapon" within Google, and it is also the least likely open source project of Google, and Kubernetes is developed on this theoretical basis. The figure below is Google's public infrastructure stack described in the Google Omega paper.
insert image description here

The architecture of the Kubernetes project (as shown in the figure below) is very similar to its prototype project Borg, which consists of two nodes, Master and Node, which correspond to control nodes and computing nodes respectively.
insert image description here

  • The Master node is also the control node. It is the center of the entire cluster and is Stateful. It is responsible for maintaining the state of the entire Kubernetes cluster. It consists of three independent components: kube-apiserver for API services, kube-scheduler for scheduling, and kube-controller-manager for container orchestration. The persistent data of the entire cluster is processed by kube-api-server and stored in Etcd. In order to ensure a single responsibility, the Master node generally does not deploy containers.

    Borg's guidance to Kubernetes is reflected in the Master node. Although the implementation details of Borg and Kubernetes' Master nodes may be different, their starting point is the same, that is, how to arrange, manage, and schedule jobs submitted by users.

  • The Node node is also the computing node, which is where the deployed container actually runs. The core of it is the kubelet component (there will also be a kubelet component on the master node). Kubelet is mainly responsible for dealing with the container runtime (such as the Docker project), and uses the remote call interface of CRI (Container Runtime Interface). This interface defines the core operations of the container runtime, such as all the parameters required to start a container. This is why the Kubernetes project does not care what container runtime you are using. As long as the container runtime can run standard container images, it can be connected to the Kubernetes project by implementing CRI.

    Specific container runtimes, such as the Docker project, generally interact with the underlying Linux operating system through the OCI container runtime specification, that is, translate CRI requests into calls to the Linux operating system, such as calling Namespace and Cgroups.

    In addition, kubelet also interacts with Device Plugin through the gRPC protocol. This plug-in is the main component used by Kubernetes to manage physical host devices such as GPUs. It is also a function that must be paid attention to for machine learning training and high-performance job support based on Kubernetes projects.

    Kubelet can also call network plug-ins and storage plug-ins to configure network and persistent storage for containers through CNI (Container Networking Interface) and CSI (Container Storage Interface) interfaces respectively.

    The name kubelet comes from the cognate component Borglet in the Borg project. However, the Borg project does not support container technology, but simply uses Linux Cgroups to limit the process. This also means that "container images" like Docker do not exist in Borg, and naturally there is no need to manage container images, but Google uses a package management tool called Midas Package Manager (MPM) internally. , it can partially replace the role of the Docker image. In addition, Borglet components do not need to consider how to interact with Docker, nor do they need to support many container technology interfaces such as CRI, CNI, and CSI. It can be said that kubelet is a component re-implemented to realize Kubernetes' container management capabilities, and has no direct inheritance relationship with Borg.

The Kubernetes project did not use Docker as the core of the entire architecture like various "container cloud" projects at the same time, but only implemented it as the lowest-level container runtime. It is equivalent to viewing Docker as a new application packaging method, so Borg's past experience in large-scale job management and orchestration can be directly applied to the Kubernetes project.

CRI

And in 2014, Docker was in its heyday, K8s was just born, and while it had support from Google and Borg, it was still relatively new.

Therefore, K8s first chose to support Docker.

Fast forward to 2016, one year after CNCF was established, and K8s also released version 1.0, which can be officially used in production environments. These all show that K8s has grown up.

So he announced to join CNCF and became the first CNCF hosting project. It wants to use the power of the foundation to unite with other manufacturers to "defeat" Docker.

In version 1.5 at the end of 2016, K8s introduced a new interface standard: CRI: Container Runtime Interface container runtime interface.

CRI uses ProtoBuffer and gPRC to specify how the kubelet should call the container runtime to manage containers and images, but this is a new set of interfaces that are completely incompatible with previous Docker calls.

Obviously, it does not want to be bound to Docker anymore, and allows access to other container technologies (such as rkt, kata, etc.) at the bottom layer, and can "kick off" Docker at any time.

But at this time Docker is very mature, and the inertia of the market is also very strong. It is impossible for major cloud vendors to replace Docker all at once.

Therefore, K8s can only provide a "compromise" solution at the same time, adding an "adapter" between kubelet and Docker to convert Docker's interface into a CRI-compatible interface:
insert image description here

Because this "adapter" is sandwiched between kubeletDocker and Docker, it is aptly called "shim", which means "shim".

With CRI and shim, although K8s still uses Docker as the underlying runtime, it also has the conditions for decoupling from Docker, thus opening the curtain of "abandoning Docker".

Containerd

Facing the challenge, Docker adopted the strategy of "surviving with a broken arm" to promote its own reconstruction, splitting the original single-architecture Docker Engine into multiple modules, of which the Docker daemon part was donated to CNCF, and containerd was formed.

As a CNCF hosted project, containerd must be CRI compliant. However, due to many reasons, Docker is only called by containerd in Docker Engine, and the external interface remains unchanged, that is to say, it is not compatible with CRI.

Due to Docker's "stubbornness", there are two call chains in K8s at this time:

  • Use the CRI interface to call dockershim, then dockershim calls Docker, and Docker goes to containerd
    to operate the container.
  • Use the CRI interface to directly call containerd to operate the container.

insert image description here

Obviously, because containerd is used to manage containers, the final effect of the two call chains is exactly the same, but the second method removes the two links of dockershim and Docker Engine, which is more concise and clear, and has better performance.

When Kubernetes 1.10 was released in 2018, containerd was also updated to version 1.1, officially integrated with Kubernetes, and published a [blog post](https://kubernetes.io/blog/2018/05/24/kubernetes-containerd-integration-gos-ga / "blog post") to display some performance test data:
insert image description here

From these data, it can be seen that compared with Docker 18.03 at that time, the containerd1.1Pod startup delay has been reduced by about 20%, the CPU usage has been reduced by 68%, and the memory usage has been reduced by 12%. Such a considerable performance improvement is beneficial to cloud vendors. It is very tempting to say.

Deprecate Docker

In 2020, K8s 1.20 finally officially "declares war" on Docker: kubelet will deprecate Docker support and will be completely removed in future versions.

But since Docker has become almost synonymous with container technology, and K8s has been using Docker for years, the announcement quickly "smelled" as it spread, with "kubelet will deprecate Docker support" reduced to something more eye-catching "K8s will Deprecated "Docker".

This naturally caused panic in the IT industry, and "people who didn't know the truth" expressed their shock:

Docker, which has been used for so long, suddenly cannot be used.

Why does K8s treat Docker like this?

Will the previous investment in Docker go to zero? What about the large number of existing images?

In fact, if you understand the two projects CRI and containerd mentioned above, you will know that this move of K8s is not surprising, everything is "natural": in fact, it is just "abandoning dockershim", that is, dockershim Moving out of kubelet is not a software product that "abandons Docker".

Therefore, "abandoning Docker" has little impact on K8s and Docker, because they have changed the bottom layer to open source containerd, and the original Docker images and containers can still run normally. The only change is that K8s bypasses Docker and directly calls containerd inside Docker.
insert image description here

However, there will still be some impact. If K8s directly uses containerd to operate containers, then it is a working environment independent of Docker, and neither can access the containers and images managed by the other. In other words, using the docker ps command will not see the containers running in K8s.

It may take some people a little getting used to and using the new crictl tool, but the subcommands for viewing containers and images are still the same, such as ps, images, etc., and it's not hard to adapt (if you've been using kubectl Manage K8s, this has no effect).

K8s originally planned to complete the "docker deprecation" work in a year, but it really underestimated the foundation of Docker. The 1.23 version still failed to remove dockershim, so it had to be postponed for half a year. Finally, version 1.24 removed the dockershim code from the kubelet.

Since then, Kubernetes and Docker have completely "parted ways".

Conclusion: The future of Docker

So, what does the future hold for Docker? Is there no place for it in the cloud native era? The answer to this question is obviously no.

As the founder of container technology, no one can question Docker's historical status. Although K8s is no longer bound to Docker by default, Docker can still coexist in other forms of K8s.

First of all, since the container image format has been standardized (OCI specification, Open Container Initiative), the Docker image can still be used normally in K8s, and there is no need to change the original development test and CI/CD process. We can still pull Docker Hub, or write a Dockerfile to package the application.

Secondly, Docker is a complete software product line, not just containerd, it also includes many services such as image building, distribution, testing, and even K8s is built into Docker Desktop.

In terms of the convenience of container development, Docker is still difficult to be replaced for the time being. Most cloud-native developers can continue to work in this familiar environment, using Docker to develop applications that run in K8s.

Also, although K8s no longer includes dockershim, Docker has taken over this part of the code and built a project called cri-dockerd, which also works, adapting the Docker Engine to the CRI interface so that the kubelet can pass it again Operate Docker as if it never happened.

In general, although Docker was defeated in the container orchestration war and squeezed to the corner by K8s, it still has strong vitality. Many loyal users and a large number of application images accumulated over the years are its biggest capital and backing. Enough to support it on another path that doesn't go head-to-head with K8s.

For beginners, Docker is easy to use, has a complete tool chain, and a friendly interface. It is difficult to find comparable software on the market. It should be said to be the "best choice" for entry-level learning container technology and cloud native.

reference

[Why does K8s abandon Docker? 】https://mp.weixin.qq.com/s/qEKyEseD370xWI-2yIyUzg
【The grievance between Docker and k8s】https://www.cnblogs.com/powertoolsteam/p/14980851.html
【Why does k8s abandon docker 】https://boilingfrog.github.io/2023/01/07/why does k8s abandon docker/

This is the end of today's sharing

Welcome to like and comment

insert image description here

Guess you like

Origin blog.csdn.net/nings666/article/details/131540588