Un fatto abbastanza notorio ed evidente del ciclo di vita del software è che esso non si conclude dopo il rilascio, dopo la manutenzione: è necessario rinnovarlo periodicamente, costantemente, producendo nuove major release. Persino software sostanzialmente già completo e factotum viene ulteriormente esteso e rimesso ciclicamente sul mercato.
Alle volte si tratta di affinamenti e revamp sostanzialmente solo estetici, cioè riprogettazioni delle interfacce che non toccano minimamente il cuore centrale delle funzionalità; altre volte si rivede tutto ma per piccoli passi fra una versione e l’altra, mantenendo o recuperando quanto più possibile codice dalle versioni passate in nome della retrocompatibilità e della minimizzazione del rischio; altre volte ancora si procede a vere e proprie riscritture che condividono con le versioni precedenti solamente il nome.
Nulla di male nel rifare le cose: in certi casi si arriva al punto che qualcosa non è più facilmente espandibile, manutenibile, gestibile per cui risulta più pratico – o doveroso – ripartire da zero.
Feature parity
Il problema connesso a riscrivere un software da zero o rivederne molto codice per una nuova futura versione è pianificare il raggiungimento della cosiddetta “feature parity“, ossia l’ordine ed i tempi precisi per il ripristino totale delle funzionalità fra la nuova versione e quella precedente.
Entra sicuramente in gioco il concetto di priorità: le caratteristiche-chiave di qualunque progetto, quelle che gli garantiscono la sua esistenza e sussistenza, devono essere ripristinate il prima possibile, anzi subito.
Nel caso delle feature secondarie, si può invece tergiversare un po’ ma non troppo a lungo: ogni tanto si sente di qualche utente che si lamenta perchè la nuova versione del suo software preferito “nella versione nuova non fa più $AZIONE” e, magari, $AZIONE è qualcosa che, si dice, “solo pochi al mondo hanno mai usata in quel programma“.
Quest’ultima frase è tipica del programmatore-medio che crede di conoscere bene il suo programma (cosa tipicamente vera e si spera che sia veramente così) e, soprattutto, come viene usato dai clienti (cosa tipicamente falsa o comunque spesso parziale). Sotto sotto è un altro modo per manifestare sfiducia verso il cliente finale e/o irriderne le conoscenze tecniche: meglio tralasciare…
Morale della fiaba:
“Se inserisci una feature in un programma e poi lo rilasci, aspettati di doverla supportare a lungo e forse per sempre. Non importa se tu ritieni quella feature di primaria o secondaria importanza o mediti addirittura di eliminarla da tempo.”
Se c’è anche solo un utente che l’ha mai usata, è probabile che protesterà se nel passaggio da una major release all’altra non la reinserirai quanto prima. Realisticamente non sarà una sola persona a lamentarsi ma più d’una, magari tante. Ricorda: non puoi sapere in che mani il tuo programma finirà e come e perchè i tuoi clienti lo stanno usando.
Quello che sai è quello che conosci al momento, cioè quello che il tuo software fa ed in che modo. Quello è il punto di partenza.
Del doman non v’è certezza…
Un caso di studio: KDE 4.0
Un aspetto molto tribolato del passaggio di KDE dalla versione 3.x alla 4.x è stata la perdita di funzionalità e di programmi chiave, una “falla” che solo recentemente (4.4/4.5 e successive) è stata chiusa.
Si parla di 3 anni per arrivare alla “feature parity” rispetto alla serie precedente. Lungi da me criticare KDE, tanto più che si tratta di un progetto Open Source, portato avanti da un gran numero di volontari. Tuttavia, sul piano del software, questa fase del progetto ha rappresentato e rappresenta un ottimo caso di studio. Anche per i suoi stessi sviluppatori.
Tutto inizia nel 2006 : motivato inizialmente dal rilascio delle librerie Qt 4, gli sviluppatori di KDE si sono messi al lavoro quasi immediatamente su quello che sarebbe poi diventato KDE 4.0.
Sono stati fatti enormi passi in avanti sotto il profilo dell’infrastruttura sottostante, rimosse funzionalità e librerie deprecate, sono stati integrati e supportati nuovi standard per l’interoperatività fra desktop, è stata rivista pesantemente l’aspetto grafico, … Insomma, un nuovo progetto, un nuovo mastodontico sforzo. Tanto di cappello per averlo pensato e poi essere riusciti a realizzarlo davvero.
Il problema di questo tipo di progetto è proprio la mole di lavoro globale, ossia non solo quello degli sviluppatori del cosiddetto “core”, il nucleo su cui tutto il resto si appoggia, ma anche di quelli delle applicazioni “utente”.
Non una serie di passaggi per gradi, non un processo quasi-statico in cui ad ogni passo ci si ferma un attimo, attendendo che il sistema si stabilizzi. Si è puntato per il rinnovamento globale. Onore al coraggio!
Purtroppo, nei progetti grandi come KDE, vale la regola del:
“Più si cambia e più si rischia di dover cambiare.”
Mettiamoci nei panni di uno sviluppatore di applicazioni di KDE, non core, alle prese con questa situazione evolutiva. Se, fra una release e l’altra della piattaforma, cambiano poche API, il “porting” del mio programma sarà relativamente agevole ed immediato. Se cambiano molti dettagli, addirittura molte librerie base, ecco che il porting somiglierà sempre più ad una riscrittura del codice.
Sicuro, ogni innovazione/rinnovamento seria reca degli effetti collaterali e si spera che non sia necessario continuare a rinnovare, altrimenti gli sviluppatori di applicazioni si troveranno sempre nella brutta situazione delle guardie (sviluppatori di applicazioni) che inseguono i ladri che fuggono (sviluppatori “core”).
Se tutto ciò lo inseriamo in un contesto Open Source, un mondo frizzante dove ogni giorno si inseriscono nuove leve e se ne perdono altre, i grossi progetti tendono a diventano dispersivi sotto il profilo dello sforzo e delle risorse impiegate.
Il risultato è che magari, alla fine del tunnel, si ha un bel desktop environment, moderno e per certi aspetti innovativo, ma il programma per masterizzare che hai usato fino alla versione precedente (K3B) non è ancora pronto e chissà per quanto non lo sarà (1 anno dopo e passa). Idem per altri programmi.
Questo implica che gli utenti possono fare solo 3 cose:
- installarlo subito ma dover rinunciare ad usare i programmi a cui si era fatto il callo;
- installarlo subito ma installare anche le librerie della versione precedente più tutti i programmi che ancora mancano in quella nuova;
- smettere di usarlo e passare ad altro.
Io ho scelto la terza e, rivedendo un bel po’ di mie scelte personali, nel frattempo sono passato a GNOME 2.
Mai spingere l’utente al pentimento
KDE è un progetto Open Source e mi piace moltissimo. Non si può pretendere nulla dai suoi sviluppatori quanto piuttosto ringraziarli per l’ottimo lavoro svolto.
Però, da utente, un po’ di rabbia l’ho covata: da strenuo difensore di KDE, mi è risultato molto difficile giustificare a terzi (es: fan di GNOME) la scelta di una release nuova ed importante come KDE 4.0 ma ancora deficitaria sotto molti aspetti.
Se non fosse KDE e fosse un qualunque altro progetto commerciale, credetemi, non sarei così tenerlo nel giudizio.
Non esiste proprio rilasciare qualcosa di così incompleto ed inconcludente rispetto ad una versione precedente. Non esiste anche perchè nel mondo Open Source non ci sono deadline così stringenti tali da giustificare il rilascio di qualcosa che non sia davvero pronto:
I tre mai. Mai:
- rilasciare qualcosa che non è pronto, nemmeno se lo è “a sufficienza”;
- rilasciare una nuova versione senza poterne giustificare limitazioni e/o senza annunciare piani per il raggiungimento in tempi brevi della “feature parity”;
- lasciare il cliente nel dubbio e alla mercè del pentimento per avervi accordato (nuovamente) fiducia.
Ci sono certamente aziende commerciali che fanno soldi col mondo FOSS, ma non mi risulta che nessuno sviluppatore di KDE sia stato minacciato di licenziamento da nessuna ditta, nel timore che KDE 4.0 uscisse tardi.
Nel mondo commerciale esistono numerosi casi di nuove major release con problemi e carenze rispetto alle versioni precedenti. Tuttavia, per paura di perdere quote di mercato e fare figuracce, nel mondo del software proprietario si tenta di sistemare le cose in breve periodo, pianificando service/feature pack e correzioni in tempi brevi.
Non mancano però esempi “discutibili”, come ad esempio il ritardo nel rilascio del supporto al copia e incolla in WP7. In quel caso il Time To Market ed i ritardi accumulati sulla concorrenza hanno certamente imposto un rilascio in anticipo sui tempi, con tutte le conseguenze del caso.
Che ne pensate?
Il problema è spinoso, e le zone grigie sono tante. In generale sono d’accordo: è brutto lasciare a piedi utenti e sviluppatori perché si cambia troppo. Però il cambiamento a volte è necessario per non rischiare di ritrovarsi con un progetto che lentamente ma inesorabilmente diventa obsoleto.
Personalmente non imporrei mai una regola del tipo ‘se hai introdotto una feature non puoi MAI più rimuoverla’.
Se diventa un ramo secco diventa un ramo secco. E bon, va ‘potata’.
Più che altro è il ‘come’ rimuovere le parti ‘vecchie’ che dovrebbe essere preso attentamente in considerazione.
Avvertire utenza e sviluppatori in largo anticipo aiuta moltissimo.
Si può anche procedere con il mantenere, almeno per una major release, un banale ‘wrapper’ di una o più API, non ottimizzato ma funzionante, con l’avvertenza di passare al più presto ad una nuova versione (deprecation).
Anche per le funzionalità si può fare altrettanto, magari documentando come realizzare le stesse operazioni in modo nuovo e ‘più figo’, avvertendo che nella prossima versione sarà l’unico modo di fare una certa cosa.
Insomma: cercare la continuità anche nel rivoluzionare tutto.
Ciao, grazie per l’interessante post !
@Stefano: la regola del “non rimuovere nulla” non può essere per ovvi motivi essere applicata in modo troppo rigoroso. Ad un certo punto bisogna per forza sbarazzarsi delle cose inutili, obsolete o non più supportabili.
Concordo sul periodo di “warning” ai clienti prima della rimozione di qualcosa anche se, mi accorgo, non è una strategia molto diffusa. Ci sono aziende che quando decidono di cambiare, cambiano (vedi Apple), probabilmente perchè la retrocompatibilità portata all’estremo blocca la possibilità di innovare e rinnovare.
Ciao & grazie di essere passato! ^^
A proposito di questo post e dei commenti che abbiamo aggiunto, mi sembra che questo esempio calzi a pennello, soprattutto se si vanno ad approfondire i vari punti di contrasto tra il produttore e gli utenti.
(pensavo di prenderlo come spunto per un post, che ne dici ?)
@Stefano: sì, sì. Calza a pennello, idem un post. Ricordati anche il guscio di gomma di risarcimento agli utenti dopo l’”antennagate” dell’iPhone4…
Beh, la faccenda ‘antenna’ ho sempre cercato di vederla diversamente. Credo si sia trattato solo di un errore di progettazione (esagerato da un hype spropositato) su un prodotto peraltro nuovo, quindi ci può anche stare …
@Stefano: oh sì, ma intendevo dire che c’era già un precedente recente.