☄️ Add Terraform support to deploy Kapsule clusters

This commit is contained in:
Jérôme Petazzoni
2021-10-03 17:32:11 +02:00
parent fb8efbe29f
commit 47766be4b2
12 changed files with 300 additions and 0 deletions

8
.gitignore vendored
View File

@@ -1,9 +1,17 @@
*.pyc
*.swp
*~
prepare-vms/tags
prepare-vms/infra
prepare-vms/www
prepare-scw/.terraform*
prepare-scw/terraform.*
prepare-scw/stage2/*.tf
prepare-scw/stage2/kubeconfig.*
prepare-scw/stage2/wildcard_dns.*
slides/*.yml.html
slides/autopilot/state.yaml
slides/index.html

15
prepare-scw/README.md Normal file
View File

@@ -0,0 +1,15 @@
This directory contains a Terraform configuration to deploy
a bunch of Kubernetes clusters on Scaleway, using their managed
Kubernetes (Kapsule).
To use it:
```bash
scw init
terraform init
terraform apply
cd stage2
terraform apply
```
Edit `variables.tf` to change the number of clusters.

View File

@@ -0,0 +1,18 @@
resource "scaleway_k8s_cluster" "my_cluster" {
name = var.cluster_name
tags = var.common_tags
version = var.k8s_version
cni = var.cni
}
resource "scaleway_k8s_pool" "my_pool" {
cluster_id = scaleway_k8s_cluster.my_cluster.id
name = "pool-0"
tags = var.common_tags
node_type = var.node_type
size = var.pool_size
min_size = var.pool_min_size
max_size = var.pool_max_size
autoscaling = true
autohealing = true
}

View File

@@ -0,0 +1,11 @@
output "kubeconfig" {
value = scaleway_k8s_cluster.my_cluster.kubeconfig
}
output "cluster_id" {
value = scaleway_k8s_cluster.my_cluster.id
}
output "wildcard_dns" {
value = scaleway_k8s_cluster.my_cluster.wildcard_dns
}

View File

@@ -0,0 +1,17 @@
terraform {
required_providers {
scaleway = {
source = "scaleway/scaleway"
version = "2.0.0"
}
kubernetes = {
source = "hashicorp/kubernetes"
version = "2.0.3"
}
local = {
source = "hashicorp/local"
version = "2.1.0"
}
}
required_version = ">= 0.14"
}

View File

@@ -0,0 +1,39 @@
variable "cluster_name" {
type = string
default = "deployed-with-terraform"
}
variable "cni" {
type = string
default = "cilium"
}
variable "common_tags" {
type = list(string)
default = []
}
variable "k8s_version" {
type = string
default = "1.22.2"
}
variable "node_type" {
type = string
default = "DEV1-M"
}
variable "pool_size" {
type = number
default = 2
}
variable "pool_min_size" {
type = number
default = 1
}
variable "pool_max_size" {
type = number
default = 5
}

6
prepare-scw/locals.tf Normal file
View File

@@ -0,0 +1,6 @@
locals {
# Common tags to be assigned to all resources
common_tags = [
"created-by=terraform"
]
}

29
prepare-scw/main.tf Normal file
View File

@@ -0,0 +1,29 @@
module "kapsule_cluster" {
count = var.how_many_clusters
source = "./kapsule_cluster"
cluster_name = format("tf-%03d", count.index + 101)
}
output "kubectl_config" {
value = format("scw k8s kubeconfig install %s", split("/", module.kapsule_cluster.0.cluster_id)[1])
}
resource "local_file" "stage2" {
filename = "${path.module}/stage2/main.tf"
content = templatefile(
"${path.module}/stage2.tmpl",
{ count = var.how_many_clusters }
)
}
resource "local_file" "kubeconfig" {
count = var.how_many_clusters
filename = format("%s/stage2/kubeconfig.%03d", path.module, count.index + 101)
content = module.kapsule_cluster[count.index].kubeconfig.0.config_file
}
resource "local_file" "wildcard_dns" {
count = var.how_many_clusters
filename = format("%s/stage2/wildcard_dns.%03d", path.module, count.index + 101)
content = trimprefix(module.kapsule_cluster[count.index].wildcard_dns, "*.")
}

16
prepare-scw/providers.tf Normal file
View File

@@ -0,0 +1,16 @@
terraform {
required_providers {
scaleway = {
source = "scaleway/scaleway"
version = "2.0.0"
}
}
required_version = ">= 0.14"
}
provider "scaleway" {
#zone = "nl-ams-1"
#region = "nl-ams"
#project_id = "7ee16446-7711-4171-a7c2-4bb6f0d4c4c8"
}

136
prepare-scw/stage2.tmpl Normal file
View File

@@ -0,0 +1,136 @@
terraform {
required_providers {
kubernetes = {
source = "hashicorp/kubernetes"
version = "2.0.3"
}
}
required_version = ">= 0.14"
}
%{ for index in range(101, 101+count) ~}
provider "kubernetes" {
alias = "kapsule_cluster_${index}"
config_path = "$${path.module}/kubeconfig.${index}"
}
resource "kubernetes_namespace" "sshpod_${index}" {
provider = kubernetes.kapsule_cluster_${index}
metadata {
name = "sshpod"
}
}
resource "kubernetes_deployment" "sshpod_${index}" {
provider = kubernetes.kapsule_cluster_${index}
metadata {
name = "sshpod"
namespace = kubernetes_namespace.sshpod_${index}.metadata.0.name
}
spec {
selector {
match_labels = {
app = "sshpod"
}
}
template {
metadata {
labels = {
app = "sshpod"
}
}
spec {
service_account_name = "sshpod"
container {
image = "jpetazzo/sshpod"
name = "sshpod"
env {
name = "PASSWORD"
value = random_string.sshpod_${index}.result
}
lifecycle {
post_start {
exec {
command = [ "sh", "-c", "curl http://myip.enix.org/REMOTE_ADDR > /etc/HOSTIP || true" ]
}
}
}
resources {
limits = {
cpu = "2"
memory = "100M"
}
requests = {
cpu = "100m"
memory = "100M"
}
}
}
}
}
}
}
resource "kubernetes_service" "sshpod_${index}" {
provider = kubernetes.kapsule_cluster_${index}
metadata {
name = "sshpod"
namespace = kubernetes_namespace.sshpod_${index}.metadata.0.name
}
spec {
selector = {
app = "sshpod"
}
port {
port = 22
target_port = 22
node_port = 32222
}
type = "NodePort"
}
}
resource "kubernetes_service_account" "sshpod_${index}" {
provider = kubernetes.kapsule_cluster_${index}
metadata {
name = "sshpod"
namespace = kubernetes_namespace.sshpod_${index}.metadata.0.name
}
}
resource "kubernetes_cluster_role_binding" "sshpod_${index}" {
provider = kubernetes.kapsule_cluster_${index}
metadata {
name = "sshpod"
}
role_ref {
api_group = "rbac.authorization.k8s.io"
kind = "ClusterRole"
name = "cluster-admin"
}
subject {
kind = "ServiceAccount"
name = "sshpod"
namespace = "sshpod"
}
}
resource "random_string" "sshpod_${index}" {
length = 6
special = false
upper = false
}
output "ssh_${index}" {
value = format(
"ssh -l %s -p %s ssh.%s # password=%s",
"k8s",
"32222",
file(format("%s/wildcard_dns.%03d", path.module, ${index})),
random_string.sshpod_${index}.result
)
}
%{ endfor ~}

View File

@@ -0,0 +1 @@
This directory will only contain generated files.

4
prepare-scw/variables.tf Normal file
View File

@@ -0,0 +1,4 @@
variable "how_many_clusters" {
type = number
default = 2
}