Il mercato IT è da sempre caratterizzato dalla continua ricerca di tecnologie e paradigmi in grado di ottimizzare l'intero processo di gestione dei progetti software, in tutti le fasi del suo ciclo di vita. L'incredibile pervasività delle tecnologie IT ha contribuito a rendere questa esigenza ancora più stringente: sono innumerevoli i mercati in cui le tecnologie IT vengono applicate, ciascuno con esigenze differenti in termini di tempi, strategie di comunicazione e risorse disponibili.
Questo scenario ha portato alla nascita di paradigmi come CI/CD (Continuous Integration e Continuous Delivery), Agile e più in generale alla formalizzazione del modello DevOps. Questi paradigmi si fondano, seppur non direttamente, su una serie di tecnologie abilitanti, tra le quali spicca per l'appunto Docker.
Prima dell'avvento di Docker, il compito di semplificare la gestione del ciclo di vita del software (ed in particolare di quelli basati su architetture SOA) è stato affidato aalle tecnologie di virtualizzazione. Tuttavia, la pratica ha dimostrato come la virtualizzazione abbia in sé una serie di limitazioni che mal si coniugano con le esigenze delle applicazioni moderne. Se da una parte esse offrono un elevato grado di isolamento (ogni VM è di fatto un'unità a sé) dall'altra comportano un significativo spreco di risorse di calcolo, dato che ogni VM impegna l'hardware ospitante ad eseguire il codice del sistema operativo virtualizzato oltre che delle applicazioni che esegue. Ciò limita fortemente il numero di VM che uno stesso host può ospitare senza degradare le prestazioni generali del sistema. Inoltre, sebbene esistano degli standard aperti quali OVF (Open Virtualization Format), le tecnologie di virtualizzazione oggi presenti sul mercato non sono del tutto interoperabili, rendendo così le VM poco portabili: ad esempio, migrare una VM da un host VMware vSphere ad un host KVM comporta la disinstallazione dell'agent VMware tools dalla VM, la conversione delle immagini disco dal formato VMDK a RAW o QCOW, la creazione di una configurazione QEMU con hardware analogo a quello esposto da VMware (laddove ciò sia possibile) ed inifine la riconfigurazione del sistema operativo della VM (installazione di driver ed agent per i nuovi device virtuali). Tutte queste operazioni richiedono degli interventi manuali, anche solo di supervisione, e non sono esenti da rischi.
Dalla sua introduzione, Docker ha goduto di un tasso di adozione pressocché costante, divenendo di fatto una tecnologia fondamentale per lo sviluppo di applicazioni moderne. Pertanto, in questa guida illustreremo le sue caratteristiche principali e le tecnologie sulle quali si fonda, procedendo quindi con una serie di esempi pratici atti ad illustrare alcuni tipici scenari d'uso. La guida si rivolge quindi sia agli sviluppatori, che utilizzeranno Docker per testare e distribuire le proprie applicazioni, sia agli amministratori di sistema, più interessati alla gestione del servizio ed alle sue caratteristiche.
Cos'è Docker?
Docker è un progetto open source nato con lo scopo di automatizzare la distribuzione di applicazioni sotto forma di "contenitori" leggeri, portabili e autosufficienti che possono essere eseguiti su cloud (pubblici o privati) o in locale.
I "contenitori" di Docker, d'ora in poi chiamati con il termine inglese Container, sono quindi l'insieme dei dati di cui necessita un'applicazione per essere eseguita: librerie, altri eseguibili, rami del file system, file di configurazione, script, ecc.
Il processo di distribuzione di un'applicazione si riduce quindi alla semplice creazione di una Immagine Docker, ovvero di un file contenente tutti i dati di cui sopra. L'immagine viene utilizzata da Docker per creare un Container, un'istanza dell'immagine che eseguirà l'applicazione in essa contenuta.
I container sono quindi autosufficienti perché contengono già tutte le dipendenze dell'applicazione e non richiedono quindi particolari configurazioni sull'host, ma sono soprattuto portabili perché essi sono distribuiti in un formato standard (le immagini appunto), che può essere letto ed eseguito da qualunque server Docker.
Inoltre, i container sono leggeri perché sfruttano i servizi offerti dal kernel del sistema operativo ospitante, invece di richiedere l'esecuzione di un kernel virtualizzato come avviene nel caso delle VM. Ciò permette di ospitare un gran numero di container nella stessa macchina fisica.
Quest'ultimo aspetto li avvicina ad altre tecnologie di virtualizzazione leggera quali l'ormai obsoleto OpenVZ ed il suo successore LXC. Tutte si basano su alcune caratteristiche proprie del kernel Linux, ed in particolare cgroups e namespaces. Nelle lezioni successive verrà approfondito il ruolo di queste tecnologie ed il modo con cui esse vengono sfruttate da Docker e si sottolineeranno le differenze tra Docker ed LXC.
Data la sua stretta relazione con il kernel Linux, Docker è nativamente disponibile in ambiente GNU/Linux. Tuttavia, essendo uno strumento concepito per gli sviluppatori, si è resa necessaria la possibilità di eseguirlo direttamente sulle workstation, senza imporre limiti sul sistema operativo in uso. Docker è pertanto disponibile anche in ambiente macOS e Windows. In entrambi i casi, si ricorre ad una tecnologia di virtualizzazione per eseguire un kernel Linux al quale si appoggia l'engine Docker.