Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Azure Kubernets docs #1220

Merged
merged 24 commits into from
Dec 27, 2023
Merged
Show file tree
Hide file tree
Changes from 21 commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
d92fc43
doc: Add Azure kubernetes section
happyRip Nov 24, 2023
8dc7c3d
doc: Add troubleshooting
happyRip Dec 5, 2023
552908b
doc: Fix ECS deployment Database Operations CLI example
happyRip Dec 5, 2023
7d608f3
doc: Fix TTS shortcodes
happyRip Dec 7, 2023
998267f
doc: Remove emphasis from references
happyRip Dec 7, 2023
0b3786b
doc: Various fixes
happyRip Dec 7, 2023
2cf0738
doc: Add missing references
happyRip Dec 7, 2023
80a2f00
doc: Add config values
happyRip Dec 8, 2023
999a702
doc: Add a link to Azure Portal
happyRip Dec 8, 2023
6ea013f
doc: Add a warning about Bitnami Redis
happyRip Dec 8, 2023
89e5267
doc: Add deployment explanation
happyRip Dec 11, 2023
869a7d0
doc: Fix spelling
happyRip Dec 11, 2023
2817927
doc: Change `self-hosted` section name to `generic`
happyRip Dec 11, 2023
d3b3066
doc: Add Azure Architecture overview
happyRip Dec 15, 2023
c49020b
doc: Add Azure prerequisites
happyRip Dec 18, 2023
e1967b7
doc: Add an experimental warning to Azure K8s
happyRip Dec 18, 2023
851be69
doc: Restructure Kubernetes docs
happyRip Dec 18, 2023
b555eff
doc: Azure Architecture fixes
happyRip Dec 21, 2023
69c6ce8
doc: Add a note in Configuration section
happyRip Dec 21, 2023
996c51a
doc: Fix Configuration example values
happyRip Dec 21, 2023
e893af4
doc: List rights required to create resources
happyRip Dec 21, 2023
b23fca5
doc: Fix Kubernetes flavours
happyRip Dec 22, 2023
4d85076
doc: Add Azure Architecture section link
happyRip Dec 22, 2023
ccdb191
doc: Fix spelling
happyRip Dec 22, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ Alternatively, you can run ops commands using the AWS CLI:
aws ecs run-task \
--task-definition TASK_DEFINITION \
--cluster CLUSTER_NAME \
--launch-type EC2 \
--launch-type FARGATE \
--network-configuration '{
"awsvpcConfiguration":{
"subnets":[
Expand Down
23 changes: 8 additions & 15 deletions doc/content/the-things-stack/host/kubernetes/_index.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,27 +2,20 @@
title: "Kubernetes"
description: ""
weight: 3
aliases: [/getting-started/kubernetes]
---

{{% tts %}} is packaged as a [Helm Chart](https://helm.sh/) to be run on Kubernetes Clusters. {{% tts %}} Helm charts are packaged and distributed as [OCI packages](https://helm.sh/docs/topics/registries/) and are published to [Docker Hub](https://hub.docker.com/r/thethingsindustries/lorawan-stack-helm-chart).
This guide is meant for users who want to deploy {{% tts %}} on Kubernetes.

This guide helps the user to install and configure {{% tts %}} on a Kubernetes cluster.
<!--more-->

Operating The Things Stack on a Kubernetes cluster is only meant for advanced users with sufficient experience with the chosen infrastructure platform and with Kubernetes.
{{% tts %}} is currently available as two flavours for self-hosting on Kubernetes.

{{< warning >}} Until the release of v1.0.0, all versions are considered to be in the Alpha stage and are not suitable for production use. The Things Industries does not offer any guarantees on compatibility between the Alpha versions. {{</ warning >}}
1. Generic

{{< note "Make sure to follow each section of this guide in the same order as it is written without skipping any steps." />}}
- {{% tts %}} packaged as a Helm Chart with no infrastructure provided.
happyRip marked this conversation as resolved.
Show resolved Hide resolved

## UDP Gateway Support
2. Azure

UDP gateways require connection stickiness in order to continue communicating with Gateway Server instances when they get recreated or when the nodes on which Gateway Servers are running are replaced. The most straightforward way to do this is to connect UDP gateways directly to the Gateway Server service via an external Load Balancer.
This depends on the settings of the external Load Balancer that is used. The implementation details are specific to the external environment and is hence out of scope for this documentation.
Please check the documentation of the Load Balancer and run tests to ensure that gateway communication is not lost on server updates.
- {{% tts %}} deployment on Azure Kubernetes Service with Azure supporting infrastructure.

## Kubernetes Version Support

||Kubernetes v1.21 and above|
|---|---|
|Chart v1.0.0 and below (alpha)|[x]|
Read more in the following sections.
20 changes: 20 additions & 0 deletions doc/content/the-things-stack/host/kubernetes/azure/_index.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
---
title: "Azure"
description: ""
distributions: "Enterprise"
weight: 2
---

{{% tts %}} can be deployed to [Azure](https://portal.azure.com/) as a set of highly available services on Azure Kubernetes Service using Terraform and Helm.

This guide gives an overview of the architecture and shows how to deploy your own highly available {{% tts %}} cluster.
KrishnaIyer marked this conversation as resolved.
Show resolved Hide resolved

<!--more-->
KrishnaIyer marked this conversation as resolved.
Show resolved Hide resolved

{{< warning >}}
Until the release of v1.0.0, all versions are considered to be in the Alpha stage and are not suitable for production use. The Things Industries does not offer any guarantees on compatibility between the Alpha versions.
{{</ warning >}}

{{< warning >}}
Until Azure releases a new version of their managed Redis service ([Redis 7.0 support in Azure](https://learn.microsoft.com/en-us/answers/questions/1191155/redis-7-0-support-in-azure)) this deployment uses Bitnami in-cluster Redis Helm charts. They are not recommended for production use.
{{</ warning >}}
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
---
title: "Architecture"
description: ""
weight: 1
---

This page describes the architecture of a {{% tts %}} deployment on Azure.

<!--more-->

{{< figure src="azure-infrastructure.svg" alt="Azure Infrastructure" class="plain" >}}

## Networking

The main infrastructure is contained inside a Virtual Network, grouped into separate Private Subnets. Communication with the Internet is via a Network Address Translation Gateway (NAT GW). Internal load balancer (LB) is used to handle incoming traffic.

The NAT GW is assigned a Public IP Address Prefix while the LB is assigned a static Public IP Address.

## Data Storage

{{% tts %}} relies on two databases: PostgreSQL and Redis. Azure offers these databases as managed services.

We use [Azure Database for PostgreSQL](https://learn.microsoft.com/en-us/azure/postgresql/flexible-server/overview) as the relational database.

Azure offers a managed [Azure Cache for Redis Database](https://azure.microsoft.com/en-us/products/cache) service, but due to it's version not being compatible with {{% tts %}} the Redis we use is in-cluster. The newest Redis version supported by Azure Cache is 6.0, while the minimum required version of Redis for {{% tts %}} is 6.2.

User uploads of profile pictures and end device pictures are stored in public Azure Storage Containers.

## Configuration

The Azure Kubernetes deploymen of {{% tts %}} uses a combination of configuration stored as Terraform and Helm configuration files.

The configuration for interoperability with other LoRaWAN Backend Interfaces-compliant servers is stored as multiple files in a private Azure Storage Account.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
---
title: "Configuration"
description: ""
weight: 2
aliases: [/getting-started/kubernetes/azure/configuration]
---

{{% tts %}} requires a few configuration files to be prepared. In this section, we show how to create them and store them for further use.

<!--more-->

## Terraform Backend

Create a `config.azurerm.tfbackend` file and put it in `1-infrastructure`, `2-kubernetes` and one of the chosen DNS provider templates directories. We recommend `azure-dns` provider for this deployment.

```
storage_account_name = <storage_account_name>
container_name = <storage_container_name>
key = <terraform_state_file>
use_azuread_auth = true
happyRip marked this conversation as resolved.
Show resolved Hide resolved
```

## Deployment Configuration

Create a `deployment.auto.tfvars.json` file in `1-infrastructure` directory.

The following contains only the minimum mandatory fields for this configuration file. For a full list of possible values check the `variables.tf` file in this directory.

{{< note >}}
The combination of `<deployment_name>-<environment>-<cluster>` needs to be unique in a Resource Group.
{{</ note >}}

```
{
"azure_ad_admin_group_object_id": <object_id>, # Object ID of the AKS admin group.
"deployment_name": <deployment_name>, # Name of the deployment.
"environment": <environment>, # 'prod', 'staging' or 'dev'.
"cluster": <cluster>, # Cluster identifier for multi-cluster deployments.
KrishnaIyer marked this conversation as resolved.
Show resolved Hide resolved
"location": <location>, # Azure location
"resource_group": {
"create": <true|false>, # If set to `true` a new Resource Group will be created on deployment.
# Otherwise a Resource Group is going to be imported based on "name" parameter.
"name": <resource_group_name> # Optional custom Azure Resource Group name. Mandatory when "create" is set to `false`.
},
"domain": {
"name": <domain_name>, # Domain where The Things Stack is available.
"dns_zone": <dns_zone_name> # Azure DNS zone.
}
}
```

## ACME Configuration

Create an `acme.auto.tfvars.json` file in the DNS templates directory.

It is only required to set the `acme_email` field.

```
{
"acme_email": <acme_email> # ACME email that will receive notifications about expiring Certificates.
}
```

## {{% tts %}} Values

Create a `tts.values.yaml` file in the `2-kubernetes` templates directory.

The following contains only the minimum mandatory fields for this values file. For a full list of possible values check the `values.yaml` file of {{% tts %}} Helm chart.

```yaml
license:
key: <tts_license_key>
global:
deployment:
initialTenant:
tenantID: <initial_tenant_id>
adminEmail: <initial_tenant_admin_email>
adminUserID: <initial_tenant_admin_id>
adminPassword: <initial_tenant_admin_password>
```
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
---
title: "Deployment"
description: ""
weight: 3
---

This page describes the steps for deploying {{% tts %}} on Azure Kubernetes Service.

<!--more-->

## Azure Infrastructure

Start with the `1-infrastructure` templates that create the foundation for your deployment.

If you haven't done this before create a Terraform backend configuration file `config.azurerm.tfbackend`. You can read more about it in the [Configuration]({{< ref "/the-things-stack/host/kubernetes/azure/configuration#terraform-backend" >}}) section.

Initialize the Terraform state.

```bash
$ make init
```

Plan the deployment and verify everything is going to be set up correctly.

```bash
$ make plan
```

This template will deploy the Azure Kubernetes Service cluster, Azure Storage containers and Azure Database Flexible Server for Postgres, with their supporting infrastructure. You can apply it after validating the deployment plan. The deployment should take about 10 to 15 minutes. If you encounter any issues, please refer to [Troubleshooting]({{< ref "the-things-stack/host/kubernetes/azure/troubleshooting" >}}).

```bash
$ make apply
```

After the AKS cluster is deployed you can get the `kubeconfig` file next.

```bash
# Set KUBECONFIG if you don't want to override the default kubeconfig.
$ export KUBECONFIG='local.kubeconfig'

# Set KUBE_CONFIG_PATH to the location of the kubeconfig.
# If you didn't set the KUBECONFIG variable use '~/.kube/config' instead.
# Ref https://registry.terraform.io/providers/hashicorp/kubernetes/latest/docs#file-config
$ export KUBE_CONFIG_PATH="$(pwd)/${KUBECONFIG}"

$ az aks get-credentials --resource-group $(terraform output -raw resource_group_name) --name $(terraform output -raw aks_cluster_name)
```

{{< note >}}
If `var.allow_cluster_admin_access` is disabled, then `kubelogin` must be installed.
happyRip marked this conversation as resolved.
Show resolved Hide resolved
{{</ note >}}

Follow the prompt to authenticate the `kubectl`.

```bash
$ kubectl get pods
To sign in, use a web browser to open the page https://microsoft.com/devicelogin and enter the code xxxxxx to authenticate.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is the second line accidentally in bash block?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, the first line starting with a $ is the command used and the following lines are the output of that command.

```

Export the DNS values used for [DNS Infrastructure]({{< relref "#dns-infrastructure" >}}). Use the provider chosen during the [Configuration]({{< ref "/the-things-stack/host/kubernetes/azure/configuration#acme-configuration" >}}).

```bash
$ DNS_PROVIDER='<provider>'
$ make dns.values | jq > "$(git rev-parse --show-toplevel)/dns/${DNS_PROVIDER}/dns.auto.tfvars.json"
```

Export the Infrastructural values used for [Kubernetes Templates]({{< relref "#kubernetes-templates" >}}).

```bash
$ make infra.values | jq > '../2-kubernetes/infra.auto.tfvars.json'
```

## DNS Infrastructure

Now we need to set up the DNS infrastructure. Head over to the directory of the provider you chose during the last steps of the [Azure Infrastructure]({{< relref "#azure-infrastructure" >}}) section.

If you haven't done this before create a Terraform backend configuration file `config.azurerm.tfbackend`. You can read more about it in [Terraform Backend Configuration]({{< relref "/the-things-stack/host/kubernetes/azure/configuration#terraform-backend" >}}).

Initialize the Terraform state.

{{< note >}}
`KUBE_CONFIG_PATH` should point to your `kubeconfig`.

```bash
# Example
$ export KUBE_CONFIG_PATH='~/.kube/config'
```

{{</ note >}}

```bash
$ make init
```

Plan the deployment and verify everything is going to be set up correctly.

```bash
$ make plan
```

Now apply the template.

```bash
$ make apply
```

Verify the certificate is in ready state. This may take a couple of minutes after the deployment for the certificate to reach a ready state.

```bash
$ kubectl -n tts get cert
```

In case the certificate won't reach a ready state head over to [Troubleshooting Problems with ACME / Let's Encrypt Certificates](https://cert-manager.io/docs/troubleshooting/acme/).

## Kubernetes Templates

Head over to the `2-kubernetes` directory next.

If you haven't done this before create a Terraform backend configuration file `config.azurerm.tfbackend`. You can read more about it in [Terraform Backend Configuration]({{< relref "/the-things-stack/host/kubernetes/azure/configuration#terraform-backend" >}}).

Initialize the Terraform state.

```bash
$ make init
```

Plan the deployment and verify everything is going to be set up correctly.

{{< note >}}
`KUBE_CONFIG_PATH` should point to your `kubeconfig`.

```bash
# Example
$ export KUBE_CONFIG_PATH='~/.kube/config'
```

{{</ note >}}

```bash
$ make plan
```

Now apply the template.

```bash
$ make apply
```

Once all the targets are healthy and if the configuration was correct, {{% tts %}} console will be accessible at `https://<tenantID>.<domain>`.
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
---
title: "Prerequisites"
description: ""
weight: 1
aliases: [/getting-started/kubernetes/azure/prerequisites]
---

This section contains prerequisites for deploying {{% tts %}} on Azure Kubernetes Service.

<!--more-->

## Tools

1. [Terraform](https://www.terraform.io/)
2. [`kubectl`](https://kubernetes.io/docs/reference/kubectl/)
3. [Helm version 3](https://helm.sh/docs/intro/). Check the version of Helm installed using `helm version`. Helm v3.8 or above is required.
happyRip marked this conversation as resolved.
Show resolved Hide resolved

## License

{{% tts %}} requires a license key to run. Please [contact our sales team](mailto:[email protected]) for your license key.

## (Optional) Packet Broker Access

{{% tts %}} contains the Packet Broker Agent component that can communicate with [Packet Broker](https://packetbroker.net/).

Packet Broker is disabled by default in the Helm charts. When enabled, it can operate either only a Forwarder or as both a Forwarder and a Home Network. Check the [Packet Broker section]({{< ref "/the-things-stack/packet-broker" >}}) for more details.

- If the cluster acts simply as a Forwarder that forwards traffic to Packet Broker, then all that is needed are access credentials.
- If the cluster also needs to work as a Packer Broker Home Network, in addition to the access credentials, the cluster either needs a NetID from the LoRa Alliance or The Things Industries can lease a DevAddr Block.

Please [contact our sales team](mailto:[email protected]) for access credentials and a Device Address Block (if necessary).

## Azure

We recommend creating an Azure Resource Group (RG) for this deployment during the preparation stage. If you intend to manage the RG with Terraform you can import it into the `tfstate` later during the deployment.

After creating the RG we recommend to set up Azure Storage for Terraform backend. You can read more about this in [Azure Documentation](https://learn.microsoft.com/en-us/azure/developer/terraform/store-state-in-azure-storage).
KrishnaIyer marked this conversation as resolved.
Show resolved Hide resolved

You need to have rights to create the following resources in the RG:

- Azure Kubernetes Service
- Azure Database for PostgreSQL Flexible Server
- NAT Gateway
- Private DNS Zone
- Public IP Address
- Public IP Prefix
- Storage Account
- User Assigned Managed Identity
- Virtual Network
- Log Analytics Workspace (optional)
Loading
Loading