Implantação do Swift no Kubernetes: da compilação local ao cluster de produção
\nSwift não é apenas uma linguagem para iOS e macOS. Graças a frameworks como Vapor e Kitura, o Swift está sendo cada vez mais usado para escrever aplicações de servidor. Mas como entregar essa aplicação aos usuários? A resposta é Kubernetes. Neste guia, vamos abordar como empacotar uma aplicação Swift em Docker, configurar CI/CD e implantá-la em um cluster K8s. Você aprenderá quais são as nuances da compilação do Swift no Linux, como otimizar a imagem e como escrever os manifestos corretos para o Kubernetes.
\n\n1. Preparação da aplicação Swift para conteinerização
\nA primeira coisa que um desenvolvedor encontra é o Swift no Linux. Se você escreve no macOS, precisa fazer uma compilação cruzada da aplicação para Linux (amd64/arm64). Vamos considerar um exemplo baseado no Vapor 4.
\nCriaremos uma aplicação HTTP simples:
\n// Sources/App/routes.swift\nimport Vapor\n\nfunc routes(_ app: Application) throws {\n app.get { req async in\n "Hello from Swift on Kubernetes!"\n }\n app.get("health") { req async in\n "OK"\n }\n}\n\nPara compilar no Linux, usamos a imagem oficial do Swift. Criaremos um Dockerfile com compilação em duas etapas:
# Primeira etapa: compilação\nFROM swift:5.9-focal as builder\nWORKDIR /app\nCOPY Package.swift Package.resolved ./\nRUN swift package resolve\nCOPY . .\nRUN swift build -c release --static-swift-stdlib\n\n# Segunda etapa: imagem mínima\nFROM ubuntu:22.04\nRUN apt-get update && apt-get install -y ca-certificates libsqlite3-0 && rm -rf /var/lib/apt/lists/*\nWORKDIR /app\nCOPY --from=builder /app/.build/release/Run .\nEXPOSE 8080\nCMD ["./Run"]\n\nO ponto-chave é a flag --static-swift-stdlib. Ela ativa a vinculação estática da biblioteca padrão do Swift, o que reduz o tamanho da imagem e simplifica a implantação. Sem ela, a imagem pode pesar 1+ GB.
2. Compilação da imagem e envio para o registry
\nCompilamos a imagem e enviamos para o Docker Hub (ou qualquer outro registry):
\n# Compilação\ndocker build -t myrepo/swift-k8s-demo:1.0.0 .\n\n# Teste local\ndocker run -p 8080:8080 myrepo/swift-k8s-demo:1.0.0\ncurl http://localhost:8080\n# Resposta: Hello from Swift on Kubernetes!\n\n# Envio para o registry\ndocker push myrepo/swift-k8s-demo:1.0.0\n\nOtimização de tamanho: a imagem baseada em ubuntu:22.04 pesa ~150 MB. Se usar alpine, é possível reduzir para 50 MB, mas será necessário resolver o problema com glibc (o Swift a exige). Recomenda-se usar imagens oficiais do Ubuntu ou Debian.
3. Manifestos Kubernetes para a aplicação Swift
\nAgora vamos implantar nossa aplicação no cluster. Criaremos um Deployment e um Service.
\ndeployment.yaml:
\napiVersion: apps/v1\nkind: Deployment\nmetadata:\n name: swift-app\n labels:\n app: swift-app\nspec:\n replicas: 3\n selector:\n matchLabels:\n app: swift-app\n template:\n metadata:\n labels:\n app: swift-app\n spec:\n containers:\n - name: swift-app\n image: myrepo/swift-k8s-demo:1.0.0\n ports:\n - containerPort: 8080\n livenessProbe:\n httpGet:\n path: /health\n port: 8080\n initialDelaySeconds: 5\n periodSeconds: 10\n readinessProbe:\n httpGet:\n path: /health\n port: 8080\n initialDelaySeconds: 3\n periodSeconds: 5\n resources:\n requests:\n memory: "64Mi"\n cpu: "100m"\n limits:\n memory: "128Mi"\n cpu: "250m"\n\nservice.yaml:
\napiVersion: v1\nkind: Service\nmetadata:\n name: swift-app-service\nspec:\n selector:\n app: swift-app\n ports:\n - protocol: TCP\n port: 80\n targetPort: 8080\n type: ClusterIP\n\nObserve as probes (sondas).