Creating VMs Using OpenTofu#

OpenTofu https://opentofu.org/ is an infrastructure as code tool (IaC). It is a fork of Terraform. Opentofu is currently one of the most popular infrastructure automation tools available. VSC Cloud provides an OpenTofu module to simplify VM provisioning: https://search.opentofu.org/module/hpcugent/opennebula/vsc/latest.

Installing OpenTofu#

The client is available for different Operating Systems like Windows, Linux or macOS (https://opentofu.org/docs/intro/install/) If you cannot install it, is also available from the HPC-UGent Tier-2 login nodes at login.hpc.ugent.be.

If you are using OpenTofu on your local machine, the VSCode Extension is also recommended.

Create credentials for OpenTofu#

Tofu requires a username and a login token to authenticate to the Opennebula API. Obtaining a login token is explained in: application credentials. After obtaining the token, place it in ~/.one/one_auth on the HPC-UGent Tier-2 login node (login.hpc.ugent.be) or on your local machine if you have installed OpenTofu and/or the One CLI. The file should be in this format (replace vscxxx with your username and token with your login token):

vscxxx:token

For additional security, change the file permissions so only you can access it:

chmod 600 ~/.one/one_auth

Danger

Do not share your credential file (~/.one/one_auth) or put this file in a public place.

Tip

You can easily access and edit the files on the login node by going to the HPC-UGent Tier-2 web portal. Enable “Show Dotfiles” to see the .one directory. If it is not there, you may have to create it.

You can also access the a shell session on one of the login nodes in the HPC-UGent Tier-2 web portal (under Clusters dropdown).

Using the OpenTofu module#

You can connect via SSH to a HPC-UGent login node login.hpc.ugent.be to use OpenTofu. Login to the login node with your VSC account first:

ssh -A vscxxxxx@login.hpc.ugent.be

Important

It is important to forward your ssh agent with -A when SSH-ing to the login node.

You can use the examples on Github as a starting point. Make sure to copy the providers.tf and the main.tf files into your project directory. On linux you can use this snippet:

mkdir -p MyVSCCloudProject
wget https://github.com/hpcugent/terraform-vsc-opennebula/blob/0.0.9/examples/simple-server/main.tf
wget https://github.com/hpcugent/terraform-vsc-opennebula/blob/0.0.9/examples/simple-server/providers.tf

Tip

Make sure you have created the ~/.one/one_auth file. (see previous section).

Basic VM configuration#

Tip

If you are not using the HPC-UGent Tier-2 login nodes, you need to make sure to:

  1. Install OpenTofu

  2. Optional Install Opennebula client:

    1. Add the repository for your linux distro

    2. Install opennebula-tools with your package manager

In the previous section we created a MyVSCCloudProject directory and copied some tofu files into it. Let’s take a look at the Simple Server example’s main.tf.

This file contains the most basic configuration for a virtual machine. It consists of two modules. A module is convenient grouping of OpenTofu resources. A module has a source and a version. The source points to the VSC module on the OpenTofu Registry. The version determines the version of the module you are using. You can view the documentation specific to the version you’re using on the OpenTofu registry.

We need three things for our basic setup:

The Router#

Tip

Full router module documentation can be found here

module "router" {
  source  = "hpcugent/opennebula/vsc//modules/router"
  version = "0.0.9"
  # VM Which we can ssh to by default
  access_vm = module.SimpleVM.router_access
}

This will provide network connectivity for all the VMs in your project. With the router, you can specify the access VM, being the VM exposed to the internet through SSH. It will also be the default target for port forwarding rules

Note

There can only be one regular router per Opennebula group, except an optional VSC router.

Danger

If your router is deleted (via tofu destroy, for example) your public IP address might change. Avoid deleting your router(s), as we cannot manually assign/restore a specific IP to your project.

Port Forwarding#

You can open ports with the port-forwards block:

  port_forwards = {
    "http" = {
      external_port = 80
    }
    "https" = {
      external_port = 443
    }
  }

By default these will target the access_vm, but you can override internal_ip. For example, to add an ssh port for a second VM:

    "http_secondary" = { # Define a port forward rule for the second VM
      external_port = 51001
      internal_port = 22
      internal_ip   = module.Secondary.ip # For a VM module named "Secondary".
    }

Tip

external_port must be between 51001 and 59999 (Except for the vsc router)

Warning

Changing the port-forwarding rules will re-create the router VMs, so there may be a network interruption when the changes are applied.

The VM#

Tip

Full module documentation can be found here

module "SimpleVM" {
  source     = "hpcugent/opennebula/vsc"
  version    = "0.0.9"
  vm_name    = "SimpleExample"
  image_name = "Rocky 10"
  is_windows = false
  cpu           = 4
  memory        = 8 #Gib
  rootdisk_size = 30
}

This code will create a virtual machine with the Rocky 10 OS image provided by VSC Cloud. You can see which other images are available either with the oneimage list command or in the VSC Cloud Dashboard.

Advanced configuration#

Windows#

Tip

We strongly encourage you to consider linux-based alternatives. Our support for Windows is more limited.

Setting is_windows = true will configure the VM slightly differently for Windows images.

Full documentation#

Warning

Be sure to match the version of the documentation/examples to the version of the module that you are using

The module has some examples which can be found on Github

You can also find documentation on all of the variables on the OpenTofu Registry

Deploying your VM#

If you have followed the previous steps now you can initialize and deploy your infrastucture to VSC Tier-1 cloud.

If you haven’t deployed anything yet, you must first initialize the modules.

Move to your project directory first:

cd ~/MyProject

Edit the file as necessary (change the VM name to something descriptive, for example.):

nano main.tf

Tip

You can also edit the files through the HPC-UGent Tier-2 web portal

Now you can run

tofu init

This command performs several different initialization steps in order to prepare the current working directory for use with the module.

Next, we can inspect which changes tofu will apply:

tofu plan

You will see a list of the resources required to deploy your infrastructure. Tofu also checks if there is any syntax error in your code. Your infrastructure is not deployed yet, review the plan and then just deploy it to VSC Tier-1 Cloud running:

tofu apply

OpenTofu will show your plan again and you will see this message:

..
..
Do you want to perform these actions?
OpenTofu will perform the actions described above.
Only ’yes’ will be accepted to approve.
Enter a value:

Type yes and press enter and wait a few minutes. If everything is correct and if you have enough quota OpenTofu will show you a message after creating all the required resources.

..
..
Apply complete! Resources: 6 added, 0 changed, 0 destroyed.

Outputs:

services = {
  "Primary VM" = [
    "ssh root@193.190.80.2",
  ]
}

Your cloud infrastructure is ready to be used.

Tip

If you forgot your VM’s details, just run tofu output If you make any changes to the template, just run tofu apply again. If you add any new VMs, tofu will ask you to run tofu init again.

Important

It is important to keep a backup of opentofu files.

Opentofu generates several files in this directory to keep track of any change in your infrastructure. If for some reason you lose these files, it will be very difficult to import them into a new OpenTofu configuration.

Special considerations for multi-user workflows#

If multiple people need to interact with the project independently, there are some additional things to consider. Because only one (or two, with VSC access) router can exist per project, the management of the router instance needs to be centralized in some way.

Tofu state#

OpenTofu uses a statefile to keep track of which resources have been created and their properties. This way, if you add another port forwarding to your router, OpenTofu knows which router to change and what changes to apply. This has the downside that anyone that needs to change the port forwarding rules, needs to have access to the statefile. The statefile may also contain sensitive information (like a password, in the case of a Windows VM), so it is important to keep this file secret.

Suggested workflows#

One tofu project for all users#

In this workflow, you share the tofu code and the statefile. You could do this on a shared filesystem, for example, if you are careful to avoid collisions (working on the files at the same time). A safer way to do this is with a Remote Backend or Cloud provider, that stores your backend remotely in a way that ensures no conflicts occur. This is often paired with git, to track changes to the code. There is a list of Remote state providers further down this article.

Note

We recommend keeping your OpenTofu code in Git, but do not put the statefile in a public repository.

One “router manager”#

Alternatively, if you do not wish to use a remote state, you could have one person responsible for managing the router and the port-forwarding. In that case, the “router manager” creates an OpenTofu project with just the router defintion. Other users in the team can then create VMs in their own local OpenTofu projects. The “router manager” will then have to add any port-forwardings to the router project, using the private IP address of the VMs created by other users in the team.

Remote State Providers#

These online services offer Remote state storage. At the time of writing they offer free tiers. This list is non-exhaustive. You can also use self-hosted options, s3, a postgres db etc. See the OpenTofu Docs for more information.

Some of these should be configured with the Cloud block and others with the Backend block.

Note

(WIP) Of these I’ve only tested Gitlab so far.

Gitlab#

Gitlab offers free tofu state management with their repositories. There are also CI/CD Components if you want to integrate CI/CD into your workflow.

HCP Terraform / Terraform Cloud#

Hashicorp offers a free tier up to 500 managed resources, which should be enough for an average usecase. You can find the documentation on their pricing/limits Here.

Warning

Terraform Cloud does not officially support OpenTofu, so we recommend only using it as a state provider and to not use any of their automation features (set execution mode to remote).

Scalr#

Scalr also offers a free tier, limited to 50 runs per month (which can be avoided by setting the run mode to local). Scalr is also compatible with OpenTofu, so their additional features can be used.

Further customization#

You can also use your own OpenTofu code to deploy your infrastructure. This task is out of the scope of this document, please refer to the official OpenTofu documentation to add you own changes https://opentofu.org/docs/ or ask the VSC Cloud admins via email at cloud@vscentrum.be.