Industry Standard for Cloud Instance Initialization: Cloud-Init
Published: 2024-06-07 06:11:27

## Introduction

Cloud-Init[1] is the industry-standard tool for initializing cloud instances across multiple platforms. It is endorsed by all leading public cloud providers and is ideal for configuring private cloud infrastructures and bare-metal environments. At boot-up, Cloud-Init detects its cloud environment, accesses any provided metadata, and initializes the system. This process may include setting up network and storage configurations, establishing SSH access keys, among other system settings. Following this, Cloud-Init processes any additional user or vendor data supplied to the instance. Whether you're creating custom Linux deployment images or launching new Linux servers, Cloud-Init is pivotal for automating and streamlining these processes.

## Current Context: Cloud-Init's Ubiquity Across Cloud Platforms

Cloud-Init has become the industry standard for initializing virtual machines in the cloud computing sector, with widespread use across all major cloud platforms. An examination of the data sources that Cloud-Init supports shows its extensive compatibility, catering to numerous cloud service providers like AWS (Amazon Web Services), Azure (Microsoft Cloud), and Alibaba Cloud, as well as various private cloud and container virtualization solutions including CloudStack, OpenNebula, OpenStack, and LXD. This broad adoption highlights Cloud-Init's essential role in automating cloud infrastructure deployments across an array of platforms and services.
- Amazon EC2
- Alibaba cloud (AliYun)
- Azure
- Google Compute Engine
- LXD

## Objective: What Issues Does Cloud-Init Address?

Cloud-Init primarily addresses the need for rapid and automated configuration and startup of cloud instances, to efficiently adapt to the dynamic demands of the cloud computing environment. This tool was initially designed to simplify the initialization process of cloud instances. Since its inception as an open-source project, Cloud-Init has quickly gained widespread recognition and has become a standard feature supported by nearly all major cloud service providers, including Amazon Web Services, Google Cloud Platform, and Microsoft Azure.
**Challenges in Cloud Computing Deployment**
In the early stages of cloud computing, setting up and configuring virtual machines was a time-consuming and complex process, especially when dealing with large-scale configurations and dependent software installations. Although pre-configured system images could achieve rapid deployment, as computing needs diversified and architectures became more complex, this approach gradually appeared less flexible and efficient. Operations staff had to manually configure each instance, such as setting up networks, storage, SSH keys, software packages, and various other system aspects, which not only increased the workload but also heightened the possibility of errors.
**Cloud-Init's Solution**
Cloud-Init emerged to address this pain point. It allows users to automatically execute a series of customized configuration tasks at the first startup of a cloud instance, such as setting hostnames, network configurations, user management, and software package installations, significantly simplifying the deployment and management of cloud instances. By using Cloud-Init, users can customize startup scripts and configuration files for cloud instances, achieving a truly "configure once, run anywhere" capability, which greatly enhances the deployment efficiency and flexibility of cloud resources.
During the startup process of cloud instances, Cloud-Init is responsible for identifying the cloud environment in which it operates and accordingly initializing the system. This means that at first startup, the cloud instance is automatically configured with network settings, storage, SSH keys, software packages, and other various system settings, without the need for additional manual intervention.
The core value of Cloud-Init lies in providing a seamless bridge for the startup and connection of cloud instances, ensuring that the instances function as expected. For users of cloud services, Cloud-Init offers a first-time startup configuration management solution that does not require installation. For cloud providers, it offers instance settings that can be integrated with their cloud services.

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xh3j0tjr65zjz8goegck.png)
## Features and Use Cases of Cloud-Init

Cloud-Init provides a suite of capabilities designed for automated configuration and management across diverse cloud computing platforms. These features enable robust support for automated deployments and management in cloud settings, greatly improving the flexibility and efficiency of configuring cloud resources.
**Common use cases for Cloud-Init
**Cloud-Init is routinely employed to carry out custom initialization tasks prior to the actual startup of application processes. Typical initialization tasks include:
- Setting up the hostname
- Adding SSH keys
- Executing a script on the first boot
- Formatting and mounting a data disk
- Launching an Ansible playbook
- Install a DEB/RPM package.

Our project, AutoMQ[2], is a cloud-native Kafka implementation that leverages cloud infrastructure. On platforms like AWS, AutoMQ utilizes ASG and EC2 for operations when not deploying via Kubernetes. Before initiating AutoMQ, several preparatory steps and configurations are required. Here is the Cloud-Init script content from the Enterprise Edition of AutoMQ, detailing the key initialization steps:
1. Initialize the systemd service files.
2. Utilize the AWS SDK to authenticate with the ECS RAM Role, ensuring proper access to additional cloud services.
3. Set up the necessary environment variables for AutoMQ.
4. Launch the AutoMQ systemd service using a script.

```

#cloud-config

write_files:
  - path: /etc/systemd/system/kafka.service
    permissions: '0644'
    owner: root:root
    content: |
      // ignore some code...
      

  - path: /opt/automq/scripts/run.info
    permissions: '0644'
    owner: root:root
    content: |
      role=
      wal.path=
      init.finish=

runcmd:

    // ignore some code....

    echo "Start getting the meta and wal volume ids" > ${AUTOMQ_HOME}/scripts/automq-server.log
    region_id=$(curl -s http://169.254.169.254/latest/meta-data/placement/region)
    
    aws configure set default.region ${region_id} --profile ec2RamRoleProfile
    aws configure set credential_source Ec2InstanceMetadata --profile ec2RamRoleProfile
    aws configure set role_arn #{AUTOMQ_INSTANCE_PROFILE} --profile ec2RamRoleProfile
    
    instance_id=$(curl -s http://169.254.169.254/latest/meta-data/instance-id)


  - |
    echo "AUTOMQ_ENABLE_LOCAL_CONFIG=#{AUTOMQ_ENABLE_LOCAL_CONFIG}" >> ${AUTOMQ_HOME}/scripts/env.info
    // ignore some code....


  - |
    echo "export AUTOMQ_NODE_ROLE='#{AUTOMQ_NODE_ROLE}'" >> /etc/bashrc
    // ignore some code....

    source /etc/bashrc

  - sh ${AUTOMQ_HOME}/scripts/automq-server.sh up --s3url="#{AUTOMQ_S3URL}" >> ${AUTOMQ_HOME}/scripts/automq-server.log 2>&1 &
```
Note: This userdata content is incomplete and is for illustrative purposes only; it requires integration with other AutoMQ scripts and Enterprise Edition code to be fully operational.
**Why choose Cloud-Init when I have Docker or Kubernetes?**
When you think about setting up your environment, Docker and Kubernetes likely come to mind. However, it's great to know that choosing isn't necessary. Even if you opt for Docker or Kubernetes, you'll still need to install and configure their elements on your machines, which is precisely where Cloud-Init comes into play. They simply offer different abstraction levels in runtime environments; they're not mutually exclusive. Think of Cloud-Init as essentially the Dockerfile for the VM world.

## How does Cloud-Init work?

The process is broken down into two primary phases, taking place early in the boot process (local boot stage) and thereafter.
**Early Boot Stage**
In the local boot stage, before the network configuration kicks in, Cloud-Init primarily carries out the following tasks:
- Identify data sources: It determines the data source of the running instance by examining built-in hardware values. Data sources are the wellsprings of all configuration data.
- Fetch configuration data: After pinpointing the data source, Cloud-Init pulls configuration data from it. This data provides Cloud-Init with directives on the actions to take, which may encompass instance metadata (like machine ID, hostname, and network settings), vendor data, and user data (userdata). Vendor data comes from cloud providers, and user data (userdata) is usually implemented following network configurations.
- Network Configuration Writing: Cloud-Init writes network configurations and sets up DNS, prepping the system for network services to be implemented at startup.
**Late Startup Phase**
Following the network configuration, during the subsequent startup phase, Cloud-Init executes non-critical configuration tasks using vendor data and user data (userdata) to tailor the running instance. Specific tasks include:
- Configuration Management: Cloud-Init interfaces with management tools such as Puppet, Ansible, or Chef to apply intricate configurations and ensure the system remains current.
- Software Installation: At this juncture, Cloud-Init installs necessary software and performs updates to guarantee that the system is fully operational and up-to-date.
- User Accounts: Cloud-Init manages the creation and modification of user accounts, sets default passwords, and configures permissions accordingly.
- Execute User Scripts: Cloud-Init executes custom scripts included in the user data, facilitating the installation of additional software, the application of security measures, and more. It also injects SSH keys into the instance's authorized_keys file to enable secure remote access.

**Subdivision of the Startup Phase**
- Detect: Use the platform identification tool ds-identify to ascertain the platform on which the instance operates.
- Local: Functions under Cloud-Init-local.service, chiefly responsible for detecting "local" data sources and setting up network configurations.
- Network: Operates under Cloud-Init.service, which necessitates all configured networks to be active and processes user data.
- Config: Runs under cloud-config.service, executing configuration-only modules, such as runcmd.
- Final: Performs under cloud-final.service, marking the conclusion of the boot sequence, where user-defined scripts are executed.

## Differences and workflows between Cloud-Init and other tools

While Cloud-Init, Packer, and Ansible are all automation tools used in deployment and configuration, they vary in their functionality, positioning, and workflows.
- Cloud-Init is primarily designed for the initial boot and configuration stages of cloud instances.
- Packer specializes in creating immutable machine images that can be reused across various platforms.
- Ansible serves as a more comprehensive tool for configuration management and application deployment, ideal for automating system setups and deploying applications.

While there is some functional overlap, using these tools in tandem can enhance and streamline automation during different phases of deployment and management.

## Summary

This article offers an in-depth look at the functionalities and use cases of Cloud-Init, highlighting its differences from other deployment automation tools. We hope you find this information useful.

AutoMQ[2] is committed to advancing messaging and streaming systems into the cloud-native era. Our goal is to fully utilize mature, scalable cloud services to unlock the full potential of the cloud. Understanding the features, pricing, and principles of various cloud services thoroughly is essential. Moving forward, we will continue to share insights on cloud technology, striving to be your go-to cloud expert and helping everyone maximize the benefits of cloud services.


## References
[1] Cloud-Init:  https://github.com/canonical/Cloud-Init
[2] AutoMQ: https://github.com/AutoMQ/automq
[3] Introduction to Cloud-Init: https://cloudinit.readthedocs.io/en/latest/explanation/introduction.html#how-does-Cloud-Init-work