diff --git a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/apple/Apple.kt b/src/main/kotlin/org/domaindrivenarchitecture/provs/server/apple/Apple.kt deleted file mode 100644 index 55ac20f..0000000 --- a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/apple/Apple.kt +++ /dev/null @@ -1,87 +0,0 @@ -package org.domaindrivenarchitecture.provs.server.apple - -import org.domaindrivenarchitecture.provs.framework.core.Prov -import org.domaindrivenarchitecture.provs.framework.core.ProvResult -import org.domaindrivenarchitecture.provs.framework.core.remote -import org.domaindrivenarchitecture.provs.framework.core.repeatTaskUntilSuccess - - -/** - * Checks if URL "$host/apple" is available and return text "apple" - */ -fun Prov.checkAppleService(host: String = "127.0.0.1") = requireLast { - // repeat required as curl may return with "empty reply from server" or with "Recv failure: Connection reset by peer" - val res = repeatTaskUntilSuccess(12, 10) { - cmd("curl -m 30 $host/apple") - }.out?.trim() - - if ("apple" == res) { - ProvResult(true, out = res) - } else { - ProvResult(false, err = "Url $host/apple did not return text \"apple\" but returned: $res") - } -} - - -fun appleConfig() = - """ -kind: Ingress -apiVersion: networking.k8s.io/v1 -metadata: - name: apple-ingress - annotations: - kubernetes.io/ingress.class: "traefik" -spec: - rules: - - http: - paths: - - path: /apple - pathType: Prefix - backend: - service: - name: apple-service - port: - number: 5678 ---- - -kind: Pod -apiVersion: v1 -metadata: - name: apple-app - labels: - app: apple -spec: - containers: - - name: apple-app - image: hashicorp/http-echo - args: - - "-text=apple" ---- - -kind: Service -apiVersion: v1 -metadata: - name: apple-service -spec: - selector: - app: apple - ports: - - port: 5678 # Default port for image - """ - - -/** - * Example how to install k3s and add apple - */ -fun main() { - - val host = "123.34.56.78" - - remote(host, "root").task { - //installK3sServer(tlsHost = host) - //applyK3sConfig(appleConfig()) - - // optional check - checkAppleService(host) - } -} diff --git a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/domain/k3s/K3sService.kt b/src/main/kotlin/org/domaindrivenarchitecture/provs/server/domain/k3s/K3sService.kt index 0828a54..7e98ddc 100644 --- a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/domain/k3s/K3sService.kt +++ b/src/main/kotlin/org/domaindrivenarchitecture/provs/server/domain/k3s/K3sService.kt @@ -1,11 +1,7 @@ package org.domaindrivenarchitecture.provs.server.domain.k3s import org.domaindrivenarchitecture.provs.framework.core.Prov -import org.domaindrivenarchitecture.provs.server.infrastructure.CertManagerEndPoint -import org.domaindrivenarchitecture.provs.server.infrastructure.provisionK3sCertManager -import org.domaindrivenarchitecture.provs.server.infrastructure.provisionK3sInfra -import org.domaindrivenarchitecture.provs.server.infrastructure.provisionNetwork - +import org.domaindrivenarchitecture.provs.server.infrastructure.* /** * Installs a k3s server. @@ -15,11 +11,16 @@ import org.domaindrivenarchitecture.provs.server.infrastructure.provisionNetwork fun Prov.provisionK3s() = task { val loopbackIpv4 = "192.168.5.1" val loopbackIpv6 = "fc00::5:1" - val nodeIpv4 = "162.55.164.138" - val nodeIpv6 = "2a01:4f8:c010:622b::1" + val nodeIpv4 = "159.69.176.151" + val nodeIpv6 = "2a01:4f8:c010:672f::1" + val fqdn = "statistics.test.meissa-gmbh.de" provisionNetwork(loopbackIpv4 = loopbackIpv4, loopbackIpv6 = loopbackIpv6) - provisionK3sInfra(tlsName = "statistics.prod.meissa-gmbh.de", nodeIpv4 = nodeIpv4, nodeIpv6 = nodeIpv6, - loopbackIpv4 = loopbackIpv4, loopbackIpv6 = loopbackIpv6, installApple = true) + if (testConfigExists()) { + deprovisionK3sInfra() + } + provisionK3sInfra(tlsName = fqdn, nodeIpv4 = nodeIpv4, nodeIpv6 = nodeIpv6, + loopbackIpv4 = loopbackIpv4, loopbackIpv6 = loopbackIpv6) provisionK3sCertManager(CertManagerEndPoint.STAGING) + provisionK3sApple(fqdn, CertManagerEndPoint.STAGING) } diff --git a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/infrastructure/K3s.kt b/src/main/kotlin/org/domaindrivenarchitecture/provs/server/infrastructure/K3s.kt index 193d0ee..3d35469 100644 --- a/src/main/kotlin/org/domaindrivenarchitecture/provs/server/infrastructure/K3s.kt +++ b/src/main/kotlin/org/domaindrivenarchitecture/provs/server/infrastructure/K3s.kt @@ -5,26 +5,28 @@ import org.domaindrivenarchitecture.provs.framework.core.ProvResult import org.domaindrivenarchitecture.provs.framework.core.repeatTaskUntilSuccess import org.domaindrivenarchitecture.provs.framework.ubuntu.filesystem.base.* -private const val k3sConfigFile = "/etc/rancher/k3s/config.yaml" -private const val k3sCalicoFile = "/var/lib/rancher/k3s/server/manifests/calico.yaml" -private const val k3sAppleFile = "/var/lib/rancher/k3s/server/manifests/apple.yaml" -private const val certManagerDeployment = "/etc/rancher/k3s/certmanager.yaml" -private const val certManagerIssuer = "/etc/rancher/k3s/issuer.yaml" -private const val k3sInstallFile = "/usr/local/bin/k3s-install.sh" private const val k3sResourcePath = "org/domaindrivenarchitecture/provs/infrastructure/k3s/" +private const val k3sManifestsDir = "/etc/rancher/k3s/manifests/" +private const val k3sConfigFile = "/etc/rancher/k3s/config.yaml" +private const val k3sAppleFile = k3sManifestsDir + "apple.yaml" +private const val certManagerDeployment = k3sManifestsDir + "certmanager.yaml" +private const val certManagerIssuer = k3sManifestsDir + "issuer.yaml" + +private const val k3sInstallFile = "/usr/local/bin/k3s-install.sh" enum class CertManagerEndPoint { STAGING, PROD } - fun Prov.testConfigExists(): Boolean { return fileExists(k3sConfigFile) } fun Prov.deprovisionK3sInfra() = task { - //deleteFile(k3sCalicoFile, sudo = true) deleteFile(k3sInstallFile, sudo = true) + deleteFile(k3sAppleFile, sudo = true) + deleteFile(certManagerDeployment, sudo = true) + deleteFile(certManagerIssuer, sudo = true) cmd("k3s-uninstall.sh") } @@ -34,29 +36,16 @@ fun Prov.deprovisionK3sInfra() = task { * If tlsHost is specified, then tls (if configured) also applies to the specified host. */ fun Prov.provisionK3sInfra(tlsName: String, nodeIpv4: String, loopbackIpv4: String, loopbackIpv6: String, - nodeIpv6: String? = null, docker: Boolean = false, installApple: Boolean = false, - tlsHost: String? = null) = task { + nodeIpv6: String? = null, tlsHost: String? = null) = task { val isDualStack = nodeIpv6?.isNotEmpty() ?: false - if (testConfigExists()) { - deprovisionK3sInfra() - } if (!testConfigExists()) { - createDirs("/etc/rancher/k3s/", sudo = true) + createDirs(k3sManifestsDir, sudo = true) var k3sConfigFileName = "config.yaml.template" var k3sConfigMap: Map = mapOf("loopback_ipv4" to loopbackIpv4, "loopback_ipv6" to loopbackIpv6, "node_ipv4" to nodeIpv4, "tls_name" to tlsName) if (isDualStack) { k3sConfigFileName += ".dual" k3sConfigMap = k3sConfigMap.plus("node_ipv6" to nodeIpv6!!) - /* - createFileFromResource( - k3sCalicoFile, - "calico.yaml", - k3sResourcePath, - "644", - sudo = true - ) - */ } else { k3sConfigFileName += ".ipv4" } @@ -75,41 +64,7 @@ fun Prov.provisionK3sInfra(tlsName: String, nodeIpv4: String, loopbackIpv4: Stri "755", sudo = true ) - // TODO: does not work yet cmd("k3s-install.sh") - cmd("sh /root/k3s-install.sh") - createFileFromResource( - k3sAppleFile, - "apple.yaml", - k3sResourcePath, - "644", - sudo = true - ) - /* - - org/domaindrivenarchitecture/provs/infrastructure/k3s/config.yaml.template.template - - val tlsSanOption = tlsHost?.let { "--tls-san ${it}" } ?: "" - - val k3sAllOptions = if (tlsHost == null && options == null) - "" - else - "INSTALL_K3S_EXEC=\"$tlsSanOption ${options ?: ""}\"" - - aptInstall("curl") - if (!chk("k3s -version")) { - if (docker) { - // might not work if docker already installed - sh( - """ - curl https://releases.rancher.com/install-docker/19.03.sh | sh - curl -sfL https://get.k3s.io | $k3sAllOptions sh -s - --docker - """.trimIndent() - ) - } else { - cmd("curl -sfL https://get.k3s.io | $k3sAllOptions sh -") - } - } - */ + cmd("k3s-install.sh") } else { ProvResult(true) } @@ -139,14 +94,18 @@ fun Prov.provisionK3sCertManager(endpoint: CertManagerEndPoint) = task { } } -/* -@Suppress("unused") -fun Prov.uninstallK3sServer() = task { - cmd("sudo /usr/local/bin/k3s-uninstall.sh") -} +fun Prov.provisionK3sApple(fqdn: String, endpoint: CertManagerEndPoint) = task { + createFileFromResourceTemplate( + k3sAppleFile, + "apple.template.yaml", + k3sResourcePath, + mapOf("fqdn" to fqdn, "issuer_name" to endpoint.name.lowercase()), + "644", + sudo = true + ) + cmd("kubectl apply -f $k3sAppleFile", sudo = true) - -fun Prov.applyK3sConfig(configAsYaml: String) = task { - cmd(echoCommandForText(configAsYaml) + " | sudo k3s kubectl apply -f -") + repeatTaskUntilSuccess(10, 10) { + cmd("kubectl apply -f $certManagerIssuer", sudo = true) + } } -*/ \ No newline at end of file diff --git a/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.yaml b/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.template.yaml similarity index 76% rename from src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.yaml rename to src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.template.yaml index 68af8e1..7da24a8 100644 --- a/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.yaml +++ b/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/apple.template.yaml @@ -4,17 +4,23 @@ metadata: name: apple-ingress annotations: kubernetes.io/ingress.class: "traefik" + cert-manager.io/cluster-issuer: ${issuer_name} spec: rules: - - http: + - host: ${fqdn} + http: paths: - - path: /apple - pathType: Prefix + - pathType: Prefix + path: /apple backend: service: name: apple-service port: number: 5678 + tls: + - hosts: + - ${fqdn} + secretName: apple-cert --- kind: Pod diff --git a/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/le-issuer.template.yaml b/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/le-issuer.template.yaml index 5520201..920eb5e 100644 --- a/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/le-issuer.template.yaml +++ b/src/main/resources/org/domaindrivenarchitecture/provs/infrastructure/k3s/le-issuer.template.yaml @@ -1,13 +1,13 @@ apiVersion: cert-manager.io/v1 kind: ClusterIssuer metadata: - name: letsencrypt-${endpoint}-issuer + name: ${endpoint} spec: acme: email: admin@meissa-gmbh.de - server: https://acme${endpoint}-v02.api.letsencrypt.org/directory + server: https://acme-${endpoint}-v02.api.letsencrypt.org/directory privateKeySecretRef: - name: letsencrypt-${endpoint}-account-key + name: ${endpoint} solvers: - http01: ingress: