5
votes

Utilisation de la sortie du script bash comme variable dans Terraform

Je me demandais si quelqu'un pouvait me diriger dans la bonne direction, je cherche à verbaliser notre version de Kubernetes dans notre module Terraform tel qu'il est actuellement codé en dur.

De temps en temps, nous obtenons une erreur disant que notre "orchestration version "n'est pas valide lorsque nous déployons notre cluster - cela est dû au fait qu'Azure abandonne notre version Kubernetes ... (Nous déployons quotidiennement nos envs dev / uat)

J'ai donc eu l'idée d'utiliser une variable pour notre version afin que nous puissions toujours déployer en évitant l'erreur "orchestration invalide". J'ai écrit le script bash pour ce dont j'ai besoin;

az aks get-versions --location westeurope --query 'orchestrators' -o tsv | awk '{print $3}' | tail -2 | head -n 1

Mais maintenant je souhaite utiliser la sortie de ^^^ pour l'utiliser comme version de Kubernetes dans notre module Terraform que nous déployons quotidiennement .

Quelqu'un peut-il me diriger dans la bonne direction?

J'ai jeté un œil à l'utilisation des build-args dans le conteneur du docker.


1 commentaires

Vous voulez dire que vous voulez une substitution de commande, c'est à dire. variable = $ (commande | commande | tête -n1) ?


4 Réponses :


0
votes

Une façon de résoudre ce problème est de stocker la sortie du script bash dans un fichier, et d'utiliser le fournisseur local pour lire ce fichier:

data "azurerm_kubernetes_cluster" "test" {
  name                = "myakscluster"
  resource_group_name = "my-example-resource-group"
}

et vous pouvez ensuite utiliser le fichier content via ${local_file.foo.content}.

Mais je vérifierais quelles sources de données sont disponibles dans le fournisseur azure. Vous pouvez utiliser la ressource de données azurem_kubernetes_cluster pour obtenir la version kubernetes_version de le cluster actuellement déployé:

data "local_file" "foo" {
    filename = "${path.module}/foo.bar"
}

Ce qui rend la version de kubernetes via l'attribut kubernetes_version .


0 commentaires

0
votes

Vous pouvez utiliser la substitution de commandes pour affecter le résultat d'une commande à une variable. J'ai pris la liberté de nettoyer votre traitement de texte en une seule instruction awk . Le Bash suivant doit attribuer l'avant-dernière valeur de la troisième colonne de votre sortie az à la variable kubernetes_version .

kubernetes_version=$(
  az aks get-versions -o tsv \
    --location westeurope --query orchestrators \
      |awk '{penult=ult; ult=$3} END{printf penult}'
)

C'est non testé car je n'utilise pas Azure; veuillez commenter toute question / préoccupation.


0 commentaires

0
votes

Vous pouvez facilement transmettre la sortie du script bash à un module terraform via Terraform CLI

  1. Affectez la sortie du script bash à une variable, par exemple kubernetes_version=$([your-bash-command )
  2. Dans le même fichier bash, passez cette variable via la CLI terraform. Cela ressemble à quelque chose comme ceci:
variable "md_kubernetes_version" {}

L ' action peut être planifier / détruire / appliquer . Consultez this pour plus de détails.

  1. Assurez-vous que le répertoire tf-root contient une déclaration de variable
module "kubernetes_module" {
   source = "[tf-module-directory]"
   md_kubernetes = "${var.tf_kubernetes_version}"
}
  1. Passez la variable tf_kubernetes_version de la racine au module
variable "tf_kubernetes_version" {}
  1. Assurez-vous que le répertoire tf-module-directory contient une déclaration de variable
terraform [action] -var "tf_kubernetes_version=$kubernetes_version" [some-other-options] [tf-root-directory]

Enfin, vous pouvez utiliser $ {var.md_kubernetes_version} dans votre module terraform.

Remarque: vous pouvez choisir d'ajouter une valeur par défaut pour le terraform déclaration de variable aux étapes 3 et 5 pour une version de base de Kubernetes.

J'espère que cela vous aidera!


0 commentaires

1
votes

Utilisez la source de données externe : https://www.terraform.io/docs/providers/external/data_source. html .

Le seul problème est que la sortie et l'entrée (facultative) doivent être des Jsons valides avec des limitations .

Exemple:

data "external" "myjson" {
  program = [
    "${path.module}/scriptWhichReturnsJson.sh",
  ]
  result {

  }
}

...
resource ...  {
  value = data.external.myjson.property
}


0 commentaires