Provisioning di grandi monoliti con Vagrant

Il post di oggi vorrei usarlo per tenere traccia di alcune metodologie che sto usando per il provisioning di stack pesanti e che richiedono tempi lunghissimi.

Il software interessato rientra nella categoria del “monolite”. Lo stack monolitico è una sorta di amico enorme e per portarlo in giro bisogna prendere determinate precauzioni.

È tipo Zangief…

hqdefault

Per il raggiungimento del risultato finale, ovvero il bootstrap di ambienti completi, sto implementando un giro di provisioning fatto da cookbook Chef, script shell e Rubygem custom.

Alcuni ostacoli del progetto:

  1. Per un provisioning completo ci vogliono più di 3 ore
  2. La fase di installazione e configurazione è composta da centinaia di esecuzioni di script, chiamate a servizi REST e numerosi riavvii di servizi systemd. Tutto deve essere rigorosamente idempotente.
  3. Gli errori durante il provisioning sono da evitare assolutamente. Ripartire nel mezzo dell’installazione non è mai come partire da zero.

La scelta del provisioner e per cosa usarlo

Di base, a meno che non ci siano vincoli progettuali, siamo in grado di fare quasi tutto con i più importanti configuration management tool come Chef, Puppet e Ansible.

È importante capire cosa far fare al provisioner e cosa no. Alcune operazioni che sono specifiche per il mio ambiente di laboratorio le metto tranquillamente in blocchi shell script (che alla fine è anch’esso un provisioner di Vagrant)

 
 $script = <<-SCRIPT echo I am provisioning... date > /etc/vagrant_provisioned_at
 SCRIPT

Vagrant.configure("2") do |config|
 config.vm.provision "shell", inline: $script
 end

Per usare o meno un proxy può essere utile una semplice variabile d’ambiente.

if ENV['NO_CUSTOMER_PROXY']
 config.vm.provision 'shell',
 inline: '> /etc/profile.d/proxy.sh'
 config.vm.provision 'shell',
 inline: '> /etc/environment'
 else
 config.proxy.http = 'http://CUSTOMER.PROXY.LOCAL:8080'
 config.proxy.https = 'http://CUSTOMER.PROXY.LOCAL:8080'
 config.proxy.no_proxy = ''
 end

 

Roadmap delle box

Il punto è che non vogliamo fare e rifare il lunghissimo provisioning tutte le volte ma poter “debuggare” stati diversi della macchina.
Per esempio, nel caso esistano i seguenti possibili stati:

  1. macchina con prerequisiti installati, aggiornamenti OS e personalizzazioni.
  2. macchina con monolite installato.
  3. macchina con monolite configurato.
  4. macchina con applicazioni del monolite configurate.

Rifare tutto da zero può richiedere parecchio tempo per cui ho utilizzato il “package” di Vagrant…

vagrant package --base $id --output os_ok.box; vagrant box os_ok.box
vagrant package --base $id --output monolite_ok.box; vagrant box add monolite_ok.box
vagrant package --base $id --output monolite_configurato.box; vagrant box monolite_configurato.box
vagrant package --base $id --output monolite_con_applicazioni_configurate.box; vagrant box add monolite_con_applicazioni_configurate.box

All’occorrenza, nel Vagrantfile e nel bocco relativo alla vm, ho usato la box che mi serviva in determinato punto.

Archivi pesanti in /vagrant

Durante il provisioning ho avuto bisogno di scaricare da locazioni remote archivi anche di grandi dimensioni.

Questo durante le prove  non è performante per cui i puntamenti, dei ruoli Chef nel mio caso,  sono tutti verso src: “file:////vagrant/foo.tar.gz”. Naturalmente è opportuno dichiararli nel .gitignore.

Ciao

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s