Showing posts with label Windows. Show all posts
Showing posts with label Windows. Show all posts

Thursday, March 17, 2022

Why use Vim

Depending on your preconceptions, Vim may look exotic or sexy. Let's review those assumptions and provide rational reasons to use this fantastic text editor.
Photo by Alex Knight on Unsplash

It may be possible that you heard about Vim. It may be possible that you didn't. Depending on your background, it may even be possible that have preconceptions about it. On this post, let's try to review all assumptions and provide concrete reasons to use this fantastic text editor.

This article is an adaptation of another publication made by me on Vim4us. I'm re-publishing here to a wider audience with a few tweaks.

Vim is ubiquitous

Vim has been around for almost thirty years. Due to its simplicity, ubiquity  and low resource requirements, it's the preferred editor by sysadmins worldwide.

Easy to install

Vim is also easy to install on Windows and Macs and is packaged in most Linux distros meaning that, even if it isn't installed in your system, Vim is one line from the terminal and two clicks from your software manager.

Vim is lightweight

Differently from most editors, Vim is very lightweight. The installation package is only 10 Mb and depending on your setup, memory consumption reaches  20 Mb. Compare that with most text editors, especially the Electron-based editors like Visual Studio. Install size is not less than 200Mb, memory consumption quickly 1Gb (50 times more!) while requiring 1.5Gb of storage, making it slow, even on modern hardware.

If you're running a Mac, a low end computer, a phone, or even a Raspberry Pi, Vim is definitely a good option for you.

Vim is stable

As previously said, Vim has been around for almost 30 years. And will probably be for at two more decades. Learning Vim is an excellent investment as you will be able to use your knowledge for the next two decades at least.

Compare that to the editor you use today (EclipseVisual StudioSublime TextVisual Studio Code) - can you really guarantee you'll be using them ten years from now?

Vim is language-independent

Vim works well with anything you want, as long as it's text. Vim works by default with most file formats, has locales, can be localized, supports eastern typography such as Arabic and Hebrew and comes with built-in support (including highlighting) for most languages.

Vim respects your freedom

Vim does not contain any built-in telemetry. It's (unfortunately) common theses days the companies are abusing your statistics in favor of improvements in their system. Sysadmins trust that Vim will not be reaching the network to run ad-hoc requests.

Vim is efficient

Vim is brilliant in how it optimizes your use of the keyboard. We'll talk about that later but for now, understand that its combination of multiple modes, motions, macros and other brilliant features makes it literally light-years ahead of other text editors.

Thriving Ecosystem

Stop for a second and think about which feature you couldn't live without today on your current text editor? The answer you probably be that Python or Go extension, meaning that what you'll miss is not actually about the editor but about its ecosystem.

Vim has a brilliant ecosystem. You'll find thousands of extensions covering anything you need. You can also host your extensions anywhere (on GitHub, for example) without being locked by any vendor. You could also host them in private/corporate repos just for your team or share on public directories like Vim Awesome.

Vim is ultra-customizable

Even if by default Vim has most of what you need, it's important to understand that Vim lets you change pretty much everything. For example, you can make temporary/local customizations (by using the Ex mode), permanent customizations (by changing your .vimrc) or even customizations based on file type.

Vim is always getting better

Vim is actively developed meaning that it keeps getting better. Vim users get security patches and new features all the time. Vim is also updated to accommodate the latest upgrades on modern operating systems while also supporting older systems too!

Huge Community

Vim's community is huge and you can get help easily. These days, the most active discussions happen on Vim's mailing listsStack ExchangeIRCYouTube and of course, Reddit.

Extensive documentation

Learning how to learn Vim is the key to a continuous understanding of the tool and not getting frustrated. There are many ways to get help on Vim: using its built-in help system, using the man pages and obviously, accessing the communities listed above.

Vim is free

These days it may be odd to say that Vim's free. Vim's freedom goes beyond its price, but also your freedom to modify it to your needs and deploy it wherever you want. Vim developers also have a strong commitment to helping needed people around the world.


Vim also runs GUI-less, meaning it runs on your terminal. So you get a full featured text-editor on any system you're working on, regardless if it's a local desktop or remote supercomputer. This feature is essential for sysadmins and developers who often need to modify text files on remote machines trough an SSH connection.

Rich out-of-the-box toolset

Vim comes with fantastic tooling by default: powerful search, regular expression support, syntax highlighting, text sort, integrated terminal, integrated file manager, cryptography, color schemes, plugin management and much more. All without a single plugin installed!

Vim integrates into your workflow

Differently from other text editors which force you into their thing, Vim adjusts seamlessly to your workflow via powerful customization, extension support, integrated shell support and ability to pipe data in/out from it. 

Vim can be programmed

Want to go the extra mile? Vim also has its own language, called VimL. With it you can create your own plugins and optimize even further the system to your needs.

Vim will boost your productivity

There are multiple ways Vim will boost your productivity. First, Vim's extensive use of the home row of the keyboard saves you from having to reach the arrow keys (or even worse, the mouse) to do your work. Second, with Vim you can quickly create macros to reproduce repetitive operations, third, the combination of motions, plugins, custom shortcuts and shell integration will definitely boost your productivity way more than you could imagine.

Vim will make you type better and faster

Being keyboard based, Vim's workflow based on the home row will definitely help force you to type better. With Vim you'll realize that you probably move your hands way more than you should and will significantly increase your typing speed.

Vim will make you learn more

Most editors these days do too much. Yes, part of that is imposed on us by languages that require a lot of metadata (Java and C# for example). One problem with that is that you end up relying on the text editor much more than you need. Without access to Eclipse or Visual Studio it may be possible that you'll feel the impostor syndrome

With Vim, despite being able to, you'll feel closer to your work, resulting in a better understanding of what you're doing. You'll also realize that you will learn more and memorize better the contents of what you're working on.


On this post we provided many tips why one should learn Vim. Vim is stable, ubiquitous and is supported by an engaged, growing community. Given all its features, Vim is definitely a good tool to learn now and harvest the benefits for decades to come.


See Also

Monday, January 3, 2022

Why use the terminal

The command-line (aka terminal) is a scary thing for most users. But understanding it can be a huge step in your learning journey and add a significant boost to your career in tech.

Photo by Tianyi Ma on Unsplash

Depending on your technical skills, the command-line interface (also known as CLI or terminal) may look scary. But it shouldn't! The CLI is a powerful and resourceful tool that every person aspiring greater tech skills should learn and be comfortable with. On this article, let's review many reasons why you should learn and use the command line, commonly (and often incorrectly) referred to as terminal, shell, bash and CLI. 

This article is an adaptation of another one originally published by me on Linux4us. I'm re-publishing here to a wider audience with a few tweaks.


The command-line interface (CLI) is available in every operating system, not only in Linux. Very frequently, this is where developers and system administrators spend a lot of time. But, if you want to work with Linux, development, the cloud or with technology in general, better start learning it.

Terminals are available in every operating system including Linux, Windows and Macs


CLI-based apps are much more powerful than their GUI-based equivalents. That happens because usually GUIs are usually wrappers around libraries that power both the GUIs and the terminal apps. Very frequently, these libraries contain way more functionality than what's available in the graphical interface because, as you might expect, since software development takes time and costs money to produce, developers only add to GUI apps the most popular features. 

For example, take a look at the plethora of options that the GNU find tool provides us:

Does your GUI-based find tool has all those options?


Common and repetitive tasks are also faster in the terminal with the advantage that you will be able to repeat and even schedule these tasks so they run automatically, releasing you to do actual work, leaving the repetitive tasks to computer.

For example, consider this standard development workflow:

  1. download code from GitHub
  2. make changes
  3. commit code locally
  4. push changes back to GitHub

If you were doing the above using a GUI-based git client (for example, Tortoise Git), the workflow would be similar to the below, taking you approximately 20 minutes to complete:

  1. Open Tortoise Git's web page
  2. Click Download
  3. Next -> Next -> Next -> Finish
  4. Right-click a folder in Windows Explorer (or Nautilus, or Finder) -> Select clone -> Paster the Url -> Click OK
  5. Wait for the download to Complete -> Click OK
  6. Back to Windows Explorer -> Find File -> Open it
  7. Make your changes (by probably using GEdit, KEdit or Visual Studio Code) -> Save
  8. Back to Windows Explorer
  9. Right Click -> Commit
  10. Right Click -> Push
  11. Take a deep breath

In the terminal (for example, in Ubuntu), the workflow would be equivalent to the below and could be completed in less than 2 minutes:

sudo apt update && sudo apt install git -y   # install git
git clone <url>     # clone the GitHub repo locally
vim/nano file -> save  # edit the file using a text-based editor
git commit -m <msg> # commits the file locally
git push  # push the changes back to our GitHub repo


Terminal/CLI-based tasks can be scripted (automated) and easily repeated, meaning that you will be able to optimize a big part of your workflow. Another benefit is that these scripts can be easily shared, exactly as business and professional developers do!

So let's continue the above example. Our developer realized she is wasting too much time in the GUI and would like to speed up her workflow even more. She learned some bash scripting and wrote the function below:

gcp ()
    msg="More updates";
    if [ -n "$1" ]; then
    git add ./ && git commit -m "$msg" && git push

She's happy because now she can run from the terminal, the below command as soon as she finishes her changes:

gcp <commit-msg>

What previously took 5 minutes is now is done in 2 seconds (1.8 seconds to write the commit message and 0.2 to push the code upstream). A significant improvement in her workflow. Imagine how much more productive she would be during the course of her career!

It's important to always think how can you optimize your workflow. These small optimizations add up to your productivity significantly over time.


Not only the CLI is faster and more lightweight than equivalent GUI-based applications but it's quicker to run the same commands. For example, consider a Git client like Tortoise Git. It was supposed to be lightweight (what most GUI apps aren't) but it takes 3s to completely load and uses 10Mb of memory:

Our GUI-based git client TortoiseGit

Now take a look at its CLI equivalent. git status runs in 0.3s and consumes less than 1Mb. In other words, 20 times more efficient memory-wise and 10 times faster. 

A simple CLI command is 20x more efficient and 10x faster then its GUI equivalent

Disk Space Efficient

Another advantage of terminal apps over their GUI-equivalents is reduced disk space. For example, contrast these two popular apps. Can you spot the differences?

Application    Installation Size       Total Size       Memory Usage   
Visual Studio Code        80Mb 300Mb 500Mb (on sunny days)
Nano 0.2 Mb 0.8 Mb 3 Mb
400x more efficient 375x more efficient 160x more efficient


Another important aspect is that the CLI is extensible. From it, skilled users could easily either extend its basic functionality using its built-in features like pipes and redirections combining inputs and outputs from different tools.

For example, sysadmins could list the first two users in the system who use Bash as a shell, ordered alphabetically with:

cat /etc/passwd | grep bash | cut -d : -f 1 | sort | head -2

What's interesting from the above command is how we combined 5 different tools to get the results we need. Once you master the Linux terminal, you'll too will be able to utilize these tools effectively to get work done significantly faster!

This is a more advanced topic. We'll see in future posts more details about it.


As you might expect, the terminal is extremely customizable. Everything from the prompt to functions (as seen above) and even custom keybindings can be customized. For example, In Linux, binding the shortcut Ctrl+V to open the Vim text editor on the terminal is simple. Add this to your .bashrc file:

bind '"\C-V":"vim\n"'

Extensive range of Apps

Contrary to what most newcomers thing, the terminal has apps too! You will find apps for pretty much any use case. For example:

The above list is far from comprehensive. It's just to give you an idea of what you'd be able to find in there

For example, here's the Castero Podcast app running on a terminal:

Source; GitHub

Professional Development

Want to work with Linux, as a developer or with the cloud? Another important aspect of using the terminal is that it will make you more ready for the job market. Since servers usually run Linux and don't have GUIs, you will end up having to use some of the above tools on your day-to-day work. Developers frequently use it to run repetitive tasks, becoming way more productive. So why not start now?

Learn more about your System

Hopefully at this point you realize that you will learn way more about your system and computers in general when you use the terminal. And I'm not talking solely to Linux users. Windows and Mac users will learn a lot too! This is the secret sauce that the most productive developers want you to know!

It's also a huge win for testing new tools, maintaining your system, installing software, fixing issues and tweaking as you wish.

Getting Started

Ready to get started on your terminal/CLI journey? Here's a video that may serve as a good intro: 


Every modern computer has a terminal. Learning it will save you time, allow you to automate common actions, make you learn more about your system, grow professionally and be more productive. Well worth the effort, isn't it?

See Also

Monday, June 29, 2020

How to create a custom CentOS Stream VM on Azure

There isn't a one-click experience for creating CentOS VMs in Azure. Learn how to create yours.
Photo by Robert Eklund on Unsplash

Running CentOS on Azure is great. However, getting there requires some work because none of the on Azure are available at the moment are free. On this post we will continue illustrating why one should use CentOS by deploying our own CentOS Stream VM to Azure.

With the news that Red Hat is shutting down the CentOS project, I definitely cannot recommend CentOS for your server anymore. 😌 However, it still has its value if you're developing for RHEL.

Azure Requirements

Before getting our hands dirty let's review requirements to run a custom VM on Azure:
  • Disk format: at the moment, only fixed VHD is supported;
  • Gen: Azure supports Gen1 (BIOS boot) & Gen2 (UEFI boot) Virtual machines. Gen1 worked better for me;
  • Disk Space: Minimum 7Gb of disk space;
  • Partitioning: Use default partitions instead of LVM or raid;
  • Swap: Swap should be disabled as Azure does not support a swap partition on the OS disk;
  • Virtual Size: All VHDs on Azure must have a virtual size aligned to 1 MB;
  • Supported formats: XFS is now the default file system but ext4 is still supported.

Installing CentOS on Hyper-V

The first thing that we have to do is to produce a virtual hard disk (VHD) with a bootable CentOS installed using Hyper-V as explained in detail on a previous post. Today we'll extend that setup adding what's necessary to run it on Azure. On this tutorial we will:
  1. Download the CentOS 8 Stream ISO
  2. Create a virtual hard disk (VHD) in Hyper-V
  3. Create and configure the VM in Hyper-V
  4. Install CentOS on the VM by:
    1. Specifying a software selection
    2. Configuring networking (we'll need to install software after the first boot)
    3. Configuring partitions on disk
    4. Creating accounts
    5. Modify the system to add settings required by Azure

Downloading the CentOS 8 ISO

This should be obvious to most people. In order to get our custom installed on a VHD with Hyper-V, please go ahead and download the latest ISO to your computer. We'll need that ISO to load the installer and install it to our VHD. As previously, we'll use CentOS Stream.

Creating a Virtual Hard Disk (VHD)

With the ISO downloaded, let's create a virtual hard disk (VHD) on Hyper-V. To do so, open Hyper-V Manager, click New -> Hard Disk and choose VHD on the Choose Disk Format screen:
Next, on Choose Disk Type, choose Fixed size:
In Configure Disk, set the disk size. In my tests, 6GB was a reasonable size for a simple server and enough space on the home partition:

Creating the VM

The process to create the Hyper-V VM remains the same. Make sure to review the previous post it in detail as I'll only describe the essential bits that required by the Azure customization here.

Configuring Networking

Make sure that you choose the Default Switch in Configure Networking:

Connecting the Virtual Hard Disk

On Connect Virtual Hard Disk, we'll choose Use an existing virtual hard disk and point it to the one you just created. This is necessary because Hyper-V auto-creates VHDXs by default while Azure requires VHDs:
To finish up, validate on Summary that all looks good and confirm:

Specifying the ISO

The last thing before starting up the VM is to specify the ISO as a DVD drive. That's done on Hyper-V manager by selecting DVD Drive -> Media, choosing Image file and locating yours on disk:
I also like to disable checkpoints and unset automatic start/stop actions.

Installing CentOS Stream

After starting the VM in Hyper-V, you should be prompted with the screen below. Choose Install CentOS Stream 8-stream:

The installer

After the boot ends, you should be running the installer called Anaconda. Choose your language and click Continue:

Installation Summary

On Installation Summary, we'll essentially configure software selection, network. We'll also need to setup partitions on the Installation Destination screen.

Software selection

For the software selection, we'll go with Minimal Install as I don't want to delay the process by installing what we don't need. The only requirement we'll need to install is a text editor (I'll be using Vim, my favourite text editor but feel free to use yours) so we can make the necessary changes.

During installation, click on Software Selection and choose Minimal Install:

Disk Partitioning

Because Azure requires some special settings (see requirements above), we'll need to do manual partitioning. But don't be scared, that shouldn't be complicated. We'll divide our disk in three main partitions:
  • /boot, 300Mb - where the boot files will be placed (including the kernel)
  • /, 4Gb - where all the files of the system will be placed (including software, logs, services and libraries)
  • /home, 1Gb - to store user files
  • no swap - we don't need a swap partition as Azure will privision one for us.
We'll also use XFS whenever applicable since it's the default in Azure now.

Choose your disk and click on Custom:
 On the Manual Partitioning screen, click on Standard Partition:
Add the manual partitions by clicking on the + sign below.
 The first to add is /boot. Enter 300m on the popup so you see:
Add 1GB for /home:
And the remainder (4.7G) for /:
Confirm to complete:


Enable networking as we'll need to install our text editor (and if you wish, update the instance before uploading to Azure):

Start Installation

After all the settings were entered, click continue to proceed. During install, you will be prompted with a screen similar to:
It's recommended to set a root password and to create an account. I also recommend checking the Make this user administrator option as we should be using root as little as possible:

Before the first boot

Once the installation finishes eject the virtual ISO by goint to Hyper-V manager, choosing your VM -> Settings -> DVD Drive and set it to None -> Apply:

First Boot

After ejecting the DVD and starting the VM you should see the following boot loader:
Then the following login screen after the boot finishes:

Azure Configuration

We'll now proceed with our Azure configuration. For CentOS 8, the documentation is specified here (although in less detail than on this blog post). Login as root and follow the next steps.

Testing the network

If you recall, we chose Minimum Install during the installation. That means that we don't have a text editor yet so let's proceeed with the installation as we'll need one to modify our configuration. To confirm our network can access the internet, type:

No network?

If no network is available, check the status of your connection with:
nmcli con status
If eth0 is down, we should enable eth0 to auto-get an ip from our Hyper-V Virtual switch with:
nmcli con up eth0
Try pinging again and it should work fine now.

Installing Vim

For editing files I'll install Vim, my favourite text editor. That can be done with:
dnf install vim

Whenever possible, I'll be using DNF as it's what I'm used as a Fedora user. Feel free to use Yum if you prefer it.

Configuring the network

To configure the network, the first step is to create or edit the file /etc/sysconfig/network and add the following:
You can run this as a oneliner with:
printf "NETWORKING=yes\nHOSTNAME=localhost.localdomain\n" >> /etc/sysconfig/network

Create or edit the file /etc/sysconfig/network-scripts/ifcfg-eth0 and add the following text:
Modify udev rules to avoid generating static rules for the Ethernet interface(s). These rules can cause problems when cloning a virtual machine in Microsoft Azure or Hyper-V:
ln -s /dev/null /etc/udev/rules.d/75-persistent-net-generator.rules

Modifying GRUB

Next, we'll modify the kernel boot line in your grub configuration to include additional kernel parameters for Azure. To do this, open /etc/default/grub and set GRUB_CMDLINE_LINUX to:
GRUB_CMDLINE_LINUX="rootdelay=300 console=ttyS0 earlyprintk=ttyS0 net.ifnames=0"
Rebuild the grub configuration:
grub2-mkconfig -o /boot/grub2/grub.cfg

Installing the Azure Linux Client

We'll now install the Azure Linux Client. This package is required by Azure to perform essential tasks on our VM including provisioning, networking, user management, ssh, swap, diagnostics, etc. Installing it on CentOS is super simple as the package is available in the repo:
dnf install WALinuxAgent
Then modify /etc/waagent.conf making sure you have:
ResourceDisk.SwapSizeMB=4096    ## setting swap to 4Gb
To finish off, enable it on boot with:
systemctl enable waagent

Deprovisioning and powering off

Almost there. Just run the following commands to deprovision the virtual machine and prepare it for Azure with:
waagent -force -deprovision
export HISTSIZE=010i
systemclt poweroff
The machine will shut down. Let's move to the Azure part now.

Uploading virtual hard disk to Azure

Now that our setup is complete, we'll upload our VHD to Azure so we can create new virtual machines from it. There are two ways to do this:
  1. using AzCopy (only for the brave)
  2. use Azure Storage Explorer (recommended)
Unfortunately I can't recommend using AzCopy at the moment as the tool is full of bugs. It could be that Microsoft is still learning Go 😉.

Uploading using AzCopy (only for the brave)

To upload our VHD, you should install AzCopy and install the Azure CLI. After the installations finish, close and open all PowerShell/terminal windows so all the env vars are reloaded.

Login in Azure using the CLI

Let's login to the Azure CLI by typing on a PowerShell window:
az login

Create the disk

In order to create our managed disk, first we need to determine it's actual size. To get your disk size, type the command below and copy the output as will be necessary by the upload:
wc -c <file.vhd>
Now, run a command similar to the below replacing items in <> with your data:
az disk create -n <disk-name> -g <resourcegroup> -l <region> --for-upload --upload-size-bytes <your-vhd-size> --sku standard_lrs
To upload, first we'll need to generate a SAS token with:
az disk grant-access -n <disk-name> -g <resourcegroup> --access-level Write --duration-in-seconds 86400
If you got a json response with a "accessSas" token on it, copy that url. We'll use it to upload our VHD file to Azure using the azcopy tool:
azCopy copy "<path-to-vhd>" "<sas-token>" --blob-type PageBlob
After the upload is complete, and you no longer need to write any more data to the disk, revoke the SAS. Revoking the SAS will change the state of the managed disk and allow you to attach the disk to a VM.
az disk revoke-access -n <disk-name> -g <resourcegroup>

Option 2 (Recommended): Using Azure Storage Explorer

I usually don't recommend GUIs but AzCopy is unusable at the moment. Also uploading via Azure Storage Explorer was way faster and didn't timeout on me 😒. So install Azure Storage Explorer, open a Blob container, find or create a folder and click Upload File. Select your VHD and don't forget to set it to Page Blob:
After completed, you should see your VHD on your remove blog storage folder:
Right-click it -> properties on your disk and copy the Uri:
Next, run the following command to create a VHD from that image (it should be quick):
az disk create -n <disk-name> -g <resourcegroup> -l <region> --source <your-vhd-url>
At this point our disk should be recognized by Azure:

Creating the VM

With the disk available, we're ready to create our VM with:
az vm create -g <resourcegroup> -l <region> --name <vmname> --os-type linux --attach-os-disk <disk-name>

You should now see your VM on Azure as expected:

Testing the VM

Now the fun part, let's see if this works. If you look carefully the image above, you'll see our IP listed there. We can try to ssh into it with:
ssh bruno@<ip>

Yay! Our custom CentOS VM is available on Azure and we can access remotely. From here, it's up to you to install the serices you need. Or, just play a little with it, tear it down, recreate and so on.

Security Considerations

I dream of the day we no longer have to discuss hardening our VMs on public cloud providers. Unfortunately we're not there yet. There's a lot of bots scanning for open ports and vulnerabilities on public IPs so make sure you take the necessary precautions to secure your SSH service such as preventing root login, changing the SSH port number and even banning failed login attempts.

There's also some other measures that we can take on Azure to block that traffic but that's beyond the scope of this post.


Before wrapping up, I'd like to leave a few tips. It's important to remember that a lot can go wrong here. So far we created a virtual machine on Hyper-V locally, modified the configuration, uploaded our VHD to a blob storage and ran some commands using the Azure CLI to create our resourses on Azure. What else could go wrong? Let's see next.

What's my public ip?

You can get that information on the overview or, from the shell with:

Can't access the VM via SSH

I had this error too. There are two possible problems: (1) your VM is not accessing the internet or (2) either a firewall or Azure's Networking is not properly set. Both should be fine if it's your first time accessing your VM.

The VM isn't starting up

Recheck the steps above. A solution would be running it locally from Hyper-V and make sure you didn't break it while applying the configuration.

Can't access the internet

This error may happen if your VM is incorrectly configured or if it couldn't get an IP from Azure's DHCP server. Try accessing it from the Serial Console to get insights about the eth0 ethernet adapter, IP and connection status with:
ip a                                        # check my adapters. Expected: eth0
nmcli device show eth0        # shows the status of the ethernet connection
nmcli con up eth0                 # starts the connection

The VM won't get an IP

This is probably Azure's fault as the IP should be auto-given to you by their DHCP servers. Anyhow, we can retry being assigned an ip with:
sudo dhclient

waagent is not working

Using the Serial Console, check if the agent is working and the status is active (running) with the command below:
sudo systemctl status waagent
sudo systemctl start waagent

Can't connect to my VM via SSH

This could happen if your instance can't access the internet or if the service is not running. Try connecting to it via the Azure Serial Client and check the previous steps to make sure that the VM can ping an external site. Also confirm that your public IP is correct. If you did not specify, Azure will release your previous IPs and is not guaranteed that a new one will be the same.

Virtual routing problems

If you think that the problem is related to virtual network routing in Azure, please check these links:


On this post we reviewed in detail how to create a custom CentOS Stream image and run it on Azure. For this demo we used CentOS, my favorite distro for the server but most of the information described here should also be useful for other distributions. We also demoed how to use the Azure CLI and showed some of the features Azure provides to us.


See Also

Monday, June 15, 2020

How to create a CentOS Stream VM on Hyper-V

CentOS is an powerful, secure and reliable Linux operating system for servers and for the cloud. On this post, let's learn how to install it on Hyper-v.
Photo by Krzysztof Kowalik on Unsplash

On a previous post, we reviewed the benefits of using CentOS. Since I've been using Fedora on the desktop and CentOS on the server for many years now, I thought I'd like to try it on a virtual machine with Hyper-V. Running a Linux distro on a local VM is good for testing new software, validating compatibility with your tools and learning a new system. Using Hyper-V is particularly interesting if your want to upload a custom VM to Azure.

CentOS Stream

But what's CentOS Stream? For those who don't know, CentOS Stream is a new addition to the CentOS family. As per the documentation:
CentOS Stream is a rolling-release Linux distro that exists as a midstream between the upstream development in Fedora Linux and the downstream development for Red Hat Enterprise Linux (RHEL). It is a cleared-path to contributing into future minor releases of RHEL while interacting with Red Hat and other open source developers. This pairs nicely with the existing contribution path in Fedora for future major releases of RHEL.

Why CentOS?

I reviewed in details why use CentOS on a previous blog post. Essentially, one should CentOS because CentOS is:
  • secure: CentOS comes with a LTS kernel, has embedded support for cryptography and runs SELinux.
  • very stable: updates and releases are extremely tested by the community.
  • 10-year support: you can run previous versions of CentOS knowing you'll get updates and patches for up to 10 years.
  • robust and mature ecosystem: you can find all the best open-source tools in CentOS repos
  • cloud friendly: private or public cloud? You can run CentOS on it
  • container friendly: CentOS is ready to run all your favourite container tools (LXC, LXD, Docker, Podman, etc).
  • open-source, community based: the CentOS community is receptive, supportive and eager to help.
  • multi-platform: as expected, CentOS runs on the most popular architectures.
  • validated on critical environments: CentOS runs on millions of servers worldwide including mission critical environments.
To learn more about how CentOS is being used, check their official YouTube channel.

Why developers should care about CentOS?

This blog is all about development so why should developers care about CentOS? My personal opinion is that we developers should know well not only our own tools (programming languages, databases, IDEs, etc) but also infrastructure, networking, security, cloud, devops, containers, etc. A developer that understands how their services are deployed and run, usually produces better, faster and more reliable code.

Why not just use Ubuntu everywhere?

Most people that use Ubuntu on the desktop think that an Ubuntu server or an Ubuntu container are the best alternatives. Turns out that as we saw on a previous post, there's no right or wrong, just what works best for you. Personally I find Alpine Linux is a better choice for containers, Fedora better for the desktop and CentOS, the best on servers. Another reason to stay on the RH family is that Red Hat usually releases patches faster (including security fixes for CVEs), runs on millions of servers worldwide and features fantastic free/open source software repositories.

What about the desktop?

Should we run CentOS on our desktops/laptops? The short answer is no, I wouldn't recommend CentOS for the desktop unless 1) you really need a stable system, 2) don't run recent hardware and/or 3) don't play games or run non-free software in it. Servers not only have a slower release pace and are more strict on hardware support. Personally for the desktop, I would recommend Fedora or Ubuntu. However, CentOS Stream, being a rolling release looks promising. I'd definitely like to try it out in the future.

Downloading CentOS Stream

We'll begin this demo by downloading the latest ISO with:
I'm using wget above but fell free to hit that url with your favourite browser.

Creating the Image

So let's proceed with image creation. Since most of the Hyper-V generics should be straight-forward, I'd like to point out that:
  • In my tests, Generation 1 worked better than Gen 2, so let's use that
  • We'll use VHDX - a dynamic virtual disk for Hyper-V virtual machines
  • We'll install basic a basic, gui-less CentOS server
  • The installer will require at least 7Gb of disk (including swap) and 1Gb of memory

Specifying a name

To start, let's specify a name for our VM. For mine, I'll simply name it centos:

Select a generation

We'll stick with Gen1 as it has better compatibility with our image.

Assign memory

I chose 4GB but 1GB should be enough. Using dynamic memory is preferable as it won't overload your host.

Configure networking

Choose the default switch on this one. The default switch is simply a virtual network adapter available on your Windows host so that your VMs can access the network (trough it). It's available on the networking pane on Windows.

Virtual hard disk

Select Create a virtual hard disk, enter a name and specify a location. Hyper-V will create a virtual hard disk for. VHDX is recommended as it doesn't need to pre-allocate the specified size if not in use.


Review the summary and finish.

Before the first boot

Before the first boot, we still have to select and mount our ISO so our VM boots straight from it. We can do that in the settings panel as shown below. I also like to disable checkpoints and automatic start/stop actions as we won't need that.

Booting the Image

After setting the DVD image to our ISO, we're ready to boot our image. Run it from Hyper-V and you should see the below image, Select Install CentOS on disk:
After the boot finishes, you'll be set at the Anaconda installer (the same installer used by Fedora). We'll keep things simple this time here by setting
  • Language: English/US
  • Software selection: minimum install
  • Installation Destination: default, we'll let CentOS preconfigure everything for us;

Initial screen

If you reached this point, the installer and the boot were successful. Proceed by choosing your language:

Installation Summary

Next, we're taken to the installation summary. This is where most of the configuration will happen. As seen below, the only required input is Installation Destination. Click it to proceed with the disk configuration.

Installation Destination

We'll keep things simple and choose the virtual hard disk (sda, 10Gb) and click Done:
Want to encrypt our data? Simply check the Encrypt my data option above.


I recommend enabling networking during the installation. We'll need network access to download updates. It will also auto-set networking during boot and provide an IP for our VM via its internal DHCP service.

Software Selection

It's now time to specify which features we want. I'm traditional and I prefer my servers GUI-less so let's choose Minimum Install:
All set and ready to go. Click Done and the installation should start (see below image).

Create user and set root password

During installation, you also have the opportunity to create an account and set root's password. It's recommended to do both.
When creating the user, make sure you check the "Allow sudo" option. It will add your user to the wheel group which's essentially part of the sudoers list.


After the installation is finished, turn off the VM, eject the virtual ISO and start the image again. You shouldn't expect anything fancy on your first boot. Login as root and ping an external service to validate the network is up:

Updating the System

With the network up, we can update our system by running as root:
dnf update
Most CentOS users use yum to perform system maintenance. Starting on RHEL 8, Yum v4 is nothing more than a wrapper for DNF.

Testing SSH

So let's try to connect to this VM via ssh. We can start by querying the service status with:
systemctl status sshd
With the service up, we get its IP with:
ip a
And test if you can SSH into it. For example, from my Ubuntu WSL I get:
ssh <ip>
Back at my CentOS server, I could see the remote user being logged with:

What Next?

Now that we have a working CentOS server VM running locally, what's next? The intent of installing CentOS is to familiarize with one of the leading operating systems on the cloud which you'll most likely will run into as a developer. That said, consider reading:


On this post we reviewed how to install CentOS Stream on a Hyper-V hypervisor. CentOS is a very solid choice for the server running today on millions of servers worldwide. We also discussed why developers should look to learn better not only their tools (programming languages, databases, IDEs, etc) but also infrastructure, networking, security, cloud, devops, containers, etc. A developer that understands how their applications are deployed and run, usually produces better, faster and more reliable source. And knowing CentOS and running Linux on your desktop are excellent ways to start.


See Also

About the Author

Bruno Hildenbrand