Portainer: deploying MicroK8s
Tags: microk8s, ubuntu, kubernetes, portainer
Published: 2023-07-06 16:46:31

## Introduction

Some weeks ago, I published a blog post as an answer to another blog about Rancher manager requirements.

However, one of the collateral impact of the original blog post was an unwanted publicity to another great project: Portainer.io

Their team has contacted me and we've been talking since then. They were simply 5⭐ on their response and on their DMs.

I told them how much I appreciated their project and that I fully understood they had no part on the initial blog post. And while we were discussing, they told me that they were launching a new feature: deploy a MicroK8s node directly from Portainer.

As said in the previous blog post, for anyone following me since some time, they do know my big appreciation for MicroK8s and the team at Canonical.

It was a certitude that I would test it and blog about how to use it on WSL2.

So without further due, let's see how Portainer and MicroK8s might be one of the greatest match that might go a bit unnoticed! (*note: this is purely my personal opinion*)

## Prerequisites

Here’s the list of components I used for this blog post:

- OS: Windows 11 Professional version 23H2 - channel: Insiders canary / build: 25393

- WSL2 distro: [Ubuntu 22.04](https://apps.microsoft.com/store/detail/ubuntu/9PDXGNCFSCZV)

  - Since [WSL v0.67.6](https://github.com/microsoft/WSL/releases/tag/0.67.6), systemD can be enabled in `/etc/wsl.conf`

  - Since [WSL v1.3.10]([Release 1.3.10 · microsoft/WSL (github.com)](https://github.com/microsoft/WSL/releases/tag/1.3.10)), cgroups v2 can be used without a direct impact on containers use cases

    - To enable cgroups v2, here's changes in both WSL configuration files

      ```shell
      # Windows filesystem: $env:USERPROFILE\.wslconfig
      [wsl2]
      kernelCommandLine = cgroup_no_v1=all systemd.unified_cgroup_hierarchy=1
      
      # Linux distro filesystem: /etc/wsl.conf
      [boot]
      command = sh -c 'umount /sys/fs/cgroup/unified && umount /sys/fs/cgroup/systemd && umount /sys/fs/cgroup; mount -t cgroup2 cgroup2 /sys/fs/cgroup -o rw,nosuid,nodev,noexec,relatime,nsdelegate'
      ```

  - The distro hostname has been changed in `/etc/wsl.conf`

  - Port forwarding has been disabled in `$env:USERPROFILE\.wslconfig`

- Docker: Docker Desktop (for Windows)

  - Version: 4.21.0 (113844)
  - Docker socket shared with the distro: Settings > Resources > WSL integration

- SSH keys are generated

- [Optional] Terminal Preview: [Windows Terminal](https://apps.microsoft.com/store/detail/windows-terminal-preview/9N8G5RFZ9XK3)

  - Version: 1.18.1462.0

## Deploying Portainer as a Windows container

First thing first, yes the title of this chapter is correct, not a typo.

Secondly, you could ask: why? In addition to the usual "because I can", the goal here is to show the long history of Portainer with the containers world and "back in the days", the idea of Windows containers was somehow talked about quite often.

And if the talks are less and less present today, the fact that Portainer continues to have a Windows container solution, shows their commitment to their project as open as possible in terms of backend technologies.

Finally, this will allow to have a solution working fully on your machine without any Virtual Machines involved.

### Portainer Business Edition license

The feature of deploying a MicroK8s cluster is part of the Portainer Business Edition, and not the community one.

Before anyone jumps into conclusions how bad this is or could be, let me say that I fully approve the monetization of features that are more targeted at companies rather than community overall.

And to ensure the paywall doesn't feel as hard as "if you don't pay, you cannot try/use the features", Portainer provides a "free tier" for testing purpose with few licenses.

To obtain your free tier Business Edition, go to Portainer.io and click on the `Get Started Free` button. Fill up the form and you'll receive an email with the license. Keep it handy, as we'll need it once we deployed the Portainer container.

### Starting Portainer

The full documentation on deploying Portainer Business Edition can be found [on their docs site](https://docs.portainer.io/start/install/server/docker/wcs) or their [academy site](https://academy.portainer.io/install/#/).

The step by step approach is a real good way to learn, so it's strongly advised you go through the docs or academy at least once and see the different options.

For this blog post, in order to avoid duplicated docs, only the final command will be shared:

```powershell
# Check which Docker daemon is running
docker version --format '{{json .Server.Os}}'

# [Optional] Switch the Docker daemon to Windows Containers
& 'C:\Program Files\Docker\Docker\DockerCli' -SwitchDaemon

# Create a volume, needed by Portainer
docker volume create portainer_data

# Start the Portainer Windows container
docker run -d -p 8000:8000 -p 9443:9443 --name portainer --restart always -v \\.\pipe\docker_engine:\\.\pipe\docker_engine -v portainer_data:C:\data portainer/portainer-ee:latest

# [Optional] Check if the container is running
docker ps
```

![Create a new Portainer Windows container](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/aekuzdk4p767c6jptugx.png)

> ***NOTE:** the Docker daemon can be switched from Docker Desktop tray icon too.*

Once the container is running, you can access Portainer web interface on https://localhost:9443.

![Portainer first login welcome page](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2uerlc070xmlx8sklz26.png)

> ***NOTE:** you'll get a certificate warning as the web site is using a self-signed certificate. You can trust it and will be able to see the page above.*

From here, follow the [Portainer docs]() to setup your user, enter your license, optionally add the current Docker instance as your first environment and finally see Portainer's management page.

![Portainer management page with the first environment](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/efuqss05xquslfvzt684.png)

You're now ready to deploy a brand new MicroK8s cluster from Portainer!

## Deploying MicroK8s

Before you go ahead, please note that this section if fully described in Portainers docs on [how to deploy MicroK8s](https://docs.portainer.io/admin/environments/add/kube-create/microk8s).

If it already exists, then why "duplicating it", you might ask? Well, as said above, I hate duplicating docs indeed, however the setup used, Windows containers + WSL2 target, is not covered. Which is totally fine as it might be a very edge-y case anyways. And, you'll see later, in order to make the whole environment work as intended, there's some need of Windows network configuration.

But I don't want to spoil it for you, so let's tackle this last section step by step.

### Step 1: Create new SSH credentials

As written in the docs, you'll need to use SSH to connect to the host where you want to deploy MicroK8s.

In Portainer, you'll need to create a new `Shared Credential` before the creation of a new environment.

Once again, to avoid docs duplication, you can refer to Portainer docs on how to [add SSH credentials](https://docs.portainer.io/admin/settings/credentials/ssh) for all the details. And here's the quick steps to do it:

* Click on `Settings` in the left menu to expand it and click on `Shared Credentials`
* Click on `+ Add credentials` button in the top right of the main page
* Click on the `SSH` card to select it
* Fill all requested fields in the `Credential details` section
  * **Warning:** ensure that the SSH key you'll use is also added to the `$HOME/.ssh/authorized_keys` file in your WSL2 distro!
* Click on `Add credentials` at the bottom of the main page

With the credentials created, you can continue onto the next step.

### Step 2: Create a new environment

Go to the Portainer management page and perform the following actions:

* Click on `Environments` in the left menu
* Click on `+ Add environment` button in the top right of the main page
* Click on `Create a Kubernetes cluster` card under the `Set up new environments` section
* Click on `Start Wizard` at the bottom of the main page
* Provide a name to your new cluster
  * *Example:* wslmicrok8s
* Select the correct credentials
  * *Info:* if there's only one credential, it will be selected by default
* Enter the WSL2 IP and click on `Test connections`
  * *Info:* you can get the IP from your distro with the command `hostname -I | cut -f1 -d' '`

At this stage, you should see a connection timeout error. Jump into the next smaller step to fix it.

**Step 2.1: It's all about networking**

This is normal as the networks used by Docker Desktop for the Windows containers and WSL2 are explicitly separated. So all this work to end up here?

Well, no, thankfully this issue is similar to another one which was resolved few years ago by a [WSL2 community member](https://techcommunity.microsoft.com/t5/itops-talk-blog/windows-subsystem-for-linux-2-addressing-traffic-routing-issues/ba-p/1764074).

Let's resolve the issue:

```powershell
# Check which network the Portainer container is using
## The command below assumes the container name is "portainer"
docker network ls --filter id=$(docker inspect portainer --format '{{ range.NetworkSettings.Networks}}{{.NetworkID}}{{end}}')

# Enable the Docker and WSL networks to communicate
## The command below assumes the Docker network name is "nat"
powershell.exe -c 'Get-NetIPInterface | where {$_.InterfaceAlias -eq "vEthernet (WSL)" -or $_.InterfaceAlias -eq "vEthernet (nat)" } | Set-NetIPInterface -Forwarding Enabled'
```

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/bfko6l3cfobmof2a8u58.png)

After you ran the command to connect both networks, you can go back to the Portainer management page and click on `Test connections` again.

This time, you should get a successful message stating the node is reachable.

### Provisioning the new environment

The last options of the environment are:

* Pick a Kubernetes version
* Select additional MicroK8s `Addons`
* With all the mandatory fields filled, you can click on `+ Provision environment` at the bottom of the main page
* Click on `Close`

You'll be redirected to the `Environments` page and you'll see under the `URL` column, all the different provisioning stages.

The provisioning should take few minutes and once completed, you can click on the environment name to see its details.

But what you might really want, is to see the MicroK8s cluster content, so click on `Home` at the top of the left menu, and you should see a line with your new cluster.

![MicroK8s cluster is shown in Portainer management page](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/c2c2qx7fu4p92j62ksx9.png)

**[Optional] See the provisioning from the distro**

From a WSL distro point of view, you list before and after the list of `snaps` to see the difference once MicroK8s has been deployed.

![List the snaps installed before and after the provisioning](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/diaesroiy3jprcno8teo.png)

Congratulations, you have now deployed a new MicroK8s cluster on a WSL distro while running Portainer as a Windows container.

## Conclusion

As I stated in the introduction, I was already fan of Portainer before and I can tell the software has grown a lot and the Enterprise features are also well thought.

I would like to give again a shoutout to the Portainer team for their support and overall kindness during the writing of this blog. You're an amazing team and I wish you to be very successful.

Lastly, I hope you had fun reading this blog and learnt something out of it.

> The Corsair 🏴‍☠️