Friday 12 July 2024

Introduction to Containers

 


Hardware Virtualization


Let's review the layers of service abstractions:


source: The New Era of Cloud Computing: SaaS, IaaS and PaaS | LinkedIn


Infrastructure as a service (IaaS):

  • uses Virtual Machines to virtualize the hardware
  • allows us to share compute resources with other developers
  • each developer can:
    • deploy their own operating system (OS)
    • configure the underlying system resources such as disc space, disk I/O, or networking
    • install their favorite run time, web server, database or middleware
    • build their applications in a self contained environment with access to underlying hardware (RAM, file systems, networking interfaces, etc.)
    • The smallest unit of compute is an app with its VM
      • If we want to scale it the app, we'll also scale VM which is resource and time consuming

Shortcomings of (using only) hardware virtualization


Flexibility listed above comes with a cost:
  • Guest OS might be large (several gigabytes) and take long time to boot
  • As demand for our application increases, we have to copy an entire VM and boot the guest OS for each instance of our app, which can be slow and costly

OS virtualization

  • PaaS: abstraction of the OS
  • IaaS: abstraction of hardware


Container:

  • gives the independent scalability of workloads in PaaS and an abstraction layer of the OS and hardware in IaaS. 
  • an invisible box around our code and its dependencies with limited access to its own partition of the file system and hardware
  • only requires a few system calls to create 
  • starts as quickly as a process
  • All that's needed on each host is:
    • OS kernel that supports containers
    • container runtime
In essence, the OS is being virtualized. It scales like PaaS, but gives us nearly the same flexibility as IaaS. This makes code ultra portable, and the OS and hardware can be treated as a black box. 

We can go from development to staging, to production, or from our laptop to the Cloud without changing or rebuilding anything. As an example, let's say we want to scale a web server. With a container we can do this in seconds and deploy dozens or hundreds of them depending on the size of our workload on a single host. That's just a simple example of scaling one container, running the whole application on a single host. 

However, we'll probably want to build our applications using lots of containers, each performing their own function like microservices. If we build them this way and connect them with network connections, we can make them modular, deploy easily and scale independently across a group of hosts. The hosts can scale up and down and start and stop containers as demand for our app changes or as hosts fail.


Containers: Docker overview


Let's say we need to deploy a stack of various technologies: 
  • Web server Node.js Express
  • MongoDB
  • Redis messaging system
  • Ansible as orchestration tool
If we would go about deploying them on the bare metal host or VM, each of these components needs to be compatible with running host's hardware, OS and installed dependencies and libraries. But this is usually not the case. This is therefore named Matrix from hell.

Docker helps preventing these dependency issues. E.g. we can run each of these components in its own container, which contains libraries and dependencies that the component is compatible with. 

Docker runs on top of the OS (Win, Mac, Linux etc).

Containers are completely isolated environments. They have their own processes, network interfaces, mounts...just like virtual machines except they all share the same OS kernel (which is interfacing the hardware).

Docker adds an abstraction layer over LXC (LinuX Containers). Docker is like an extension of LXC. [LXC vs Docker: Why Docker is Better | UpGuard]

Ubuntu, Fedora, SUSE and CentOS share the same OS kernel (Linux) but have different software (GUI, drivers, compilers, file systems, ...) above it. This custom software differentiates OSes between each other.

Docker containers share the underlying OS kernel. For example, Docker on Ubuntu can run any flavour of Linux which runs on the same Linux kernel as Ubuntu. This is why we can't run Windows-based container on Docker running on Linux OS - they don't share the same kernel.
Hypervisor:
  • Abstracts away hardware for the virtual machines so they can run an operating system
  • Coordinates between the machine's physical hardware and virtual machines.
container engine (e.g. Docker Engine):
  • Abstracts away an operating system so containers can run applications
  • Coordinates between the operating system and (Docker) containers
  • Docker containers are process-isolated and don't require a hardware hypervisor. This means Docker containers are much smaller and require far fewer resources than a VM.

Unlike hypervisors, Docker is not meant to virtualize and run different operating systems and kernels on the same hardware.

The main purpose of Docker is to containerise applications, ship them and run them.

In case of Docker we have: 
  • Containers (one or more) containing:
    • Application
    • Libraries & Dependencies 
  • Docker
  • OS
  • Hardware
In case of virtual machine we have:
  • Virtual Machines (one or more) containing:
    • Application
    • Libraries & Dependencies
    • OS
  • Hypervisor
  • OS
  • Hardware
Docker uses less processing powerless disk space and has faster boot up time than VMs.

Docker containers share the same kernel while different VMs are completely isolated. We can run VM with Linux on the host with Windows.

Many companies release and ship their software products as Docker images, published on Docker Hub, public Docker registry.

We can run each application from the example above in its own container:

$ docker run nodejs 
docker run mongodb
docker run redis
docker run ansible

Docker image is a template, used to create one or more containers.

Containers are running instances of images that are isolated and have their own environments and set of processes.

Dockerfile describes the image.


References: 

Google Cloud Fundamentals: Core Infrastructure | Coursera

No comments: