Fare giusto VS fare in fretta

Sappiamo tutti come ci si sente.

Inizia un progetto nuovo.

La possibilità di riscattarsi dalle schifezze del passato profuma di carta stampata. Vuoi dare il meglio e questa è la volta buona. I compromessi saranno pochi e ben calibrati.

Il mondo reale è inesorabile e pretende che tu consegni in quella fatidica data. Al cliente non interessa se hai usato MVC, ASP, SQL, Ruby, Perl o un rito voodoo. Basta che vada e che costi poco e sia facile da usare. Basta che la sua azienda possa fatturare e che nella sua carta di credito ci sia sempre disponibilità per fare il pieno alla sua Porsche Cayenne nera con cerchi di dimensioni improbabili e finestrini oscurati.

Ti senti un po’ sotto pressione e nella testa i neuroni che tifano per “fare giusto” e quelli che tifano per “fare in fretta” cominciano a scontrarsi. Allora qualche pezzo di codice ti scappa ma ti prometti che una volta consegnata una prima versione base tornerai indietro e sistemerai quel taccone e farai le cose fatte bene.

Quella promessa che ti sei appena fatto si fa chiamare debito tecnico intenzionale. Come i debiti finanziari, anche quelli tecnici hanno gli interessi. Adesso l’hai scampata andando veloce; loro però cammineranno inesorabili e, quando non avrai più il fiato per andare veloce, ti raggiungeranno e ti presenteranno il conto.
E, a quel punto…

Sulla costruzione di una squadra, prequel

In una stanza ci sono un fanboy Microsoft, uno Linux e due Apple.
La loro età media è di 25,75 anni. Ogni mattina si svegliano e cercano di battere i tasti e girare la rotellina del mouse più velocemente del giorno prima. Perché hanno voglia di fare, perché si sentono orgogliosi quando qualcosa funziona come dovrebbe e si sentono importanti a risolvere problemi dei clienti.

imagesDDGZ13FS

L’entusiasmo è la strada giusta ma intuiscono che digitare velocemente non è tutto. Intuiscono che serve qualcosa per diventare una squadra migliore.

Ed è così che decidono insieme di iniziare un percorso per capire come essere più veloci dei bug che riempiono le caselle e-mail e fanno suonare il telefono.

Non hanno ancora iniziato, presto lo faranno: agosto con le sue ferie dilata i tempi ma settembre porta con se i nuovi inizi, i nuovi propositi (un po’ come quelli per l’anno nuovo). Li vedo già curiosi e desiderosi di capire cosa potranno diventare, di guardarsi indietro tra un anno e dire “quanta strada abbiamo fatto!”.

Revisioni Tecniche Formali

Non sarebbe fantastico se esistesse un metodo per trovare circa il 60% dei difetti dei nostri software, che accorciasse i tempi di sviluppo e che quindi riducesse i costi? La bella notizia è che esiste! Questo metodo si chiama Revisione Tecnica Formale (formal inspection se vogliamo usare il gergo in inglese). È stato sviluppato da Michael Fagan all’IBM e molti studi di settore ne confermano ormai l’efficacia.

Questo tipo di revisione è efficace perché si distingue da altri metodi grazie a delle regole ben precise:

  • Utilizzo di checklist per concentrare i revisori su aree che hanno avuto problemi in passato;
  • Le revisioni hanno lo scopo di trovare difetti, non correggerli;
  • I revisori si preparano prima della riunione e partecipano con una lista di problemi da loro individuati;
  • I partecipanti hanno ruoli diversi;
  • Il moderatore della revisione non è l’autore del prodotto esaminato;
  • In ogni revisione vengono raccolti dei dati che serviranno anche per migliorare le future revisioni;
  • La dirigenza non partecipa a questo tipo di riunioni.

I ruoli

Moderatore

È il responsabile dell’andamento della revisione. Deve farla procedere a un ritmo sostenibile ma non troppo veloce, in maniera da trovare più errori possibili.

Autore

La persona che ha scritto o progettato il lavoro in esame. Svolge un compito di secondo piano in queste attività perché il codice revisionato dovrebbe “parlare da solo”. Il suo compito può essere chiarire punti oscuri.

Revisore

Chiunque ha un diretto coinvolgimento nel codice ma non ne è l’autore. Di solito il revisore trova i difetti in fase di preparazione.

Segretario

Compila il verbale della revisione registrando gli errori trovati e le assegnazioni delle attività che ne seguiranno.

Il Processo

1018px-Fagan_Inspection_Simple_flow.svg

Pianificazione

L’autore consegna il materiale al moderatore. Il moderatore decide chi parteciperà, chi revisionerà il materiale e dove.

Introduzione

Quando i revisori sono un po’ estranei al progetto in revisione, l’autore può fare un’introduzione. Questa può essere pericolosa perché potrebbe condizionare i revisori: il prodotto dovrebbe parlare da sé, non il suo autore.

Preparazione

Ogni revisore lavora in autonomia per trovare difetti con l’uso di checklist.

Riunione

Il moderatore sceglie un revisore e gli fa spiegare il codice. Tutta la logica viene spiegata, ogni ramo di ogni struttura logica. Il segretario registra gli errori quando vengono rilevati, la discussione si ferma quando un errore viene riconosciuto come tale. Il segretario annota il tipo e la severità dell’errore e la riunione prosegue. Se si accende la discussione il moderatore riporta all’ordine. Non si discutono soluzioni. La riunione dovrebbe durare meno di due ore.

Report

Entro un giorno dalla riunione il moderatore produce un report (e-mail o equivalente) che elenca ogni difetto, il suo tipo e la severità. Il report serve a garantire che ogni difetto venga corretto e per sviluppare una checklist che evidenzi problemi specifici nell’organizzazione. Si raccolgono dati sul tempo impiegato e sul numero di errori trovati nell’unità di tempo per misurare l’efficacia delle revisioni.

Rilavorazioni

Il moderatore assegna i difetti a qualcuno, molto spesso l’autore, per risolverli.

Follow-Up

Il moderatore è responsabile della verifica che il lavoro assegnato venga svolto. A seconda della gravità dei difetti corretti potrebbe (o no) seguire a lavoro ultimato un’altra revisione formale.

Non ho mai partecipato a revisioni di questo tipo ma ho la fortuna di lavorare in un ambiente dove siamo tutti aperti alle migliorie e ai cambiamenti e ne abbiamo già pianificata una tra qualche giorno. Presto faremo la prima revisione formale pilota e non vedo l’ora di toccare con mano tutti i vantaggi che finora ho solo letto studiando questo tipo di procedura. Sono sicuro che da qui a sei mesi avremmo fatto passi da giganti!

 

Noi non siamo gli utenti

Lì! Clicca lì! No, più a destra… più a destra… Clicca sul pulsante di scelta… Il pallino vuoto… (Pianta il dito sullo schermo) Ecco, qui devi cliccare.

Il miglior modo per sapere come pensa un utente è osservarlo. Chiedete a un utente di svolgere un compito “della vita reale” su un pezzo di software che state sviluppando, prendete i pop-corn, osservate e godetevi la scena.

È uno spettacolo perché nel giro di pochi secondi verranno smontate le vostre ipotesi di partenza con cui avete progettato l’UI.

Utente prende posto nella postazione a appoggia la mano sul mouse. Fissa lo schermo per qualche secondo come chiedendosi che roba è mai questa?

michael-scott3
Utente che usa il vostro programma per la prima volta

Legge qualche parola qua e là e poi proverà a fare ciò che gli avete chiesto. A questo punto vi state già accorgendo che Utente sta usando il programma in modo decisamente diverso da come l’avete immaginato. Crescerà in voi una fortissima tentazione di correggerlo, di guidarlo: la sofferenza che provate nel vedere che un’operazione da cinque secondi, per voi che avete sviluppato il programma, ci sta impiegando quasi mezzo minuto è insopportabile. Ecco allora che intervenite e dite qualcosa tipo la frase di apertura del post.

 

Quando Utente si bloccherà la prossima volta, sperando che non sia per un bug, usate le mani per prendere i pop-corn dal secchio che avete predisposto prima e riempitevi la bocca per non parlare. Probabilmente noterete che il suo sguardo si concentrerà sul punto dove è rimasto bloccato, senza andare a cercare aiuti in altri parti dell’interfaccia. Questa è una ragione del perché i menù di aiuto sono una scelta poco efficace. Le istruzioni di aiuto/messaggi di errore dovrebbero essere posizionati il più vicino possibile alla zona interessata dal problema.

RadGridView_Validation_030
Messaggio di aiuto ben posizionato.

Gli utenti usano il software intuitivamente, senza ragionare nel dettaglio. Trovano un modo che funziona per fare una cosa, anche se improprio, e poi la faranno sempre così. È meglio fornire un solo modo per fare un’operazione: il più ovvio possibile.

Tutto ciò accade perché gli utenti non passano tutto il tempo che passiamo noi al computer e, se lo fanno, è per scopi completamente diversi dai nostri. Noi usiamo il computer per il gusto di farlo: con talmente tanto gusto che il nostro mestiere che ci siamo liberamente scelti è far fare al computer ciò che vogliamo, plasmarlo al nostro volere, dominarlo. Un impiegato in ufficio invece subisce l’uso del computer: il suo lavoro è fatturare, inviare ordini ai fornitori, spostare materiale in un magazzino. Magari il computer anche lo odia, ha problemi di vista e soprattutto ragiona con schemi mentali completamente diversi da quelli che noi programmatori usiamo mille volte al giorno.

 

Rispetto del codice

Quella roba l’ha scritta Giovanni, io non la tocco! Problema suo!

Pranzando con altre persone del settore IT di altre aziende spesso sento dei “capi programmatori” che si lamentano dei loro sottoposti perché si concentrano solo sulla loro parte di codice e quando vedono errori di altri sono pronti a puntare il dito.

Non conosco nel dettaglio come mai succedano queste dinamiche in alcuni gruppi di lavoro; tuttavia penso che siano sintomo di una errata gestione delle persone, di scarsa stima e rispetto reciproco.

Credo che dovremmo aver un rispetto inteso in senso lato del codice su cui lavoriamo: per noi stessi e per i nostri compagni di team. Tutti sappiamo quanto facile sia commettere errori. In teoria potremmo, per esempio, impegnarci per lasciare il sorgente sempre un po’ migliore di come lo abbiamo trovato, prima di eseguire git push.

Cosa succederebbe se seguissimo questa semplice regola? Cosa succederebbe se ci impegnassimo a migliorare il codice, anche di poco, indipendentemente da chi sia stato l’autore originale?

Io penso che porterebbe a un sistema poco a poco sempre migliore, porterebbe a creare un intero team che ha a cuore il sorgente nella sua completezza invece di individui che tengono solamente alla loro piccola fetta…
Prendersi cura del proprio codice è un discorso. Invece, i membri di un team coeso si aiutano e si correggono a vicenda.

P.S.: A proposito di git push, un collega ha appeso questa sulla nostra lavagna

in case of git
In caso di incendio salvare il salvabile!

Atteggiamento

Quando uscite di casa, alzate il mento, su la testa, respirate profondo, bevetevi la luce del sole. Salutate gli amici con un sorriso e mettete l’anima in ogni stretta di mano. Non abbiate timore di venire fraintesi e non sprecate nemmeno un minuto a pensare ai vostri nemici. Chiaritevi bene in mente quello che volete fare e poi andate alla meta senza esitazioni. Pensate alle cose belle e positive che volete fare, un giorno, e l’occasione per coronare i vostri sogni vi si presenterà senza che neppure ve ne accorgiate. Come un animaletto del corallo succhia elementi vitali da una marea che passa e va. Immaginate nella vostra mente la persona onesta, leale, nobile che vorreste essere e cercate di somigliarle il più possibile… Il pensiero è il più forte. Conserva un corretto atteggiamento mentale, portato al coraggio, alla franchezza, alla gentilezza d’animo. Pensare nel modo giusto è già fare. Tutto proviene dal desiderio e le preghiere sincere non sono mai vane. Perseguiamo serenamente le nostre mete. Alzate il mento, su la testa. Gli uomini sono degli dei in crisalide.

– Elbert Hubbard

Il COBOL degli anni 2020

Visual Basic 6 morirà? Non a breve, per lo meno. Kale Peterson di Visual Studio Magazine lo definisce addirittura il COBOL degli anni 2020.

VB6

Quando uscì, Windows 7 sembrava l’ultimo sistema operativo su cui Microsoft avrebbe speso risorse per fare funzionare il runtime di VB6. Invece tale dichiarazione viene costantemente aggiornata e gli sforzi sono tutt’ora attivi anche per Windows 10.

Come mai? La mia esperienza mi porta a pensare che il linguaggio sia ancora supportato perché molte aziende si basano su applicazioni VB6 per processi mission critical. La maggior parte di chi programmava in VB6 non è stata in grado di fare il salto tecnologico richiesto da .NET, negli anni dove con qualche form e un database (Access!) si facevano decine di milioni di Lire/decine di migliaia di Euro. Aggravava la situazione il fatto che i tool di migrazione messi a disposizione da MS non fossero così evoluti e richiedessero molti interventi manuali (strumenti ritirati poi con Visual Studio 2010). Così i consulenti software hanno proseguito col fornire soluzioni, ricche di personalizzazioni e quindi costose. Rimpiazzare la stessa applicazione riscritta con altre tecnologie non è facilmente giustificabile da parte di un’azienda di consulenza che si trova a dover rispondere a queste domande del potenziale cliente:

  • Perché mi devo ricomprare il programma che fa le stesse cose? E quello nuovo crea anche più problemi perché meno collaudato?
  • Perché devo aggiornare quando quello che ho funziona ancora?

Pensando ad alcune risposte efficaci, si potrebbe spiegare al cliente che le tecnologie di sviluppo più recenti permettono di ottenere risultati con costi minori o più velocemente, che rendono più facili gli sviluppi su piattaforme web o mobile. Oltre al fatto che i programmatori di nuova generazione che seguiranno i progetti di tale cliente crescono a pane e Javascript, .Net, HTML; Visual Basic l’hanno sentito nominare solo per motivi storici.

Microsoft tutto ciò lo sa, lo dimostra mantenendo vivo VB6 e quindi tenendosi stretta la sua clientela.

Fare meno schifo ogni anno

Sappiamo tutti noi tecnici come ci si sente a uscire dalla propria zona di comfort e imparare linguaggi o framework nuovi: possiamo quindi capire chi non è riuscito a stare al passo coi tempi. Cala la produttività e il peso delle scadenze diventa improvvisamente maggiore. Inoltre, spiegare al proprio titolare che determinate evoluzioni sono necessarie è difficile se non è tecnologicamente informato.

Se vogliamo chiamarci programmatori di professione, però, dobbiamo trovare il modo per rimanere costantemente aggiornati fare costante pratica ed esercitarci liberamente. Non pensate che, come professionisti, dovremmo sentirci obbligati a farlo? A essere quest’anno meno schifosi dell’anno scorso?
Che ciò avvenga per motivi puramente egoistici, per mantenere vivo il nostro entusiasmo, per farci assumere dall’azienda dei sogni, per realizzare l’app del momento, per sapere cosa succede “là fuori” e come gli altri fanno le cose.
Purché avvenga.

Messaggi di errore

Ho sempre avuto un particolare interesse per i messaggi di errore. Ritengo che un software a qualunque livello (app per smartphone, l’app della tua azienda, il gestionale per la fatturazione del negozio sotto casa) debba avere i messaggi di errore che siano utili per l’utente finale (anche per il servizio assistenza se necessario o coerente con l’ambito d’utilizzo) e non fargli venire voglia di spaccare lo schermo.

IC725769
Un messaggio di errore frustrante

Niente è più demotivante di un messaggio di errore che dice tutto/niente, lasciandoti a bocca asciutta e che non ti guida verso la risoluzione del problema. I messaggi di errore frustranti fanno venire voglia di disinstallare il programma e sconsigliarne l’uso a colleghi-amici-parenti. Siccome la differenza la fanno i dettagli, quando vedo dei messaggi di errore ben scritti faccio sempre mentalmente i complimenti a chi ha creato il software.

Per messaggio di errore si intende:

Un avviso all’utente riguardo un problema che è già accaduto.

I messaggi di errore sono quindi da distinguersi rispetto alle dialog box, ai messaggi di avviso e alle conferme.

Il primo problema con i messaggi di errore è che ci sono troppi modi per farli sbagliati: troppo tecnici, troppo generici, che accusano l’utente, troppo rossi, con le scritte maiuscole, con troppo informazioni buttate alla meno peggio e via dicendo.

Perciò quando è il mio turno di scrivere dei messaggi di errore faccio il meglio che posso per renderli dei gentili avvisi per l’utente provando a renderli:

  • Informativi in un linguaggio comprensibile ai non tecnici e inerenti al dominio del problema;
    • Esportazione del bilancio non riuscita per sovraccarico del sistema, riprovare tra qualche minuto è meglio di Esportazione dei dati non riuscita per un timeout della richiesta al server;
  • Essere concisi;
  • Fornire informazioni su come venirne fuori;
  • Il pulsanti/le scelte devono avere un testo che sia un verbo d’azione che fa riferimento esplicito a come l’utente sceglie di arginare il problema, tipo: Annulla, Riprova, Conferma, Ho capito, Continua (da evitare i classici OK / Sì / No);
  • Contenere informazioni di aiuto per il reparto tecnico di assistenza, visibili all’utente tramite progressive disclosure.

Degli ottimi messaggi di errore si trovano in Git:

 

Cattura
Esempio di errore per comando non esistente in Git.

 

Cattura
Messaggio di errore di Git del comando add

 

I miei buoni propositi per i messaggi di errore non riesco sempre a mantenerli, ma è un argomento che mi sta a cuore e per questo cerco di fare meglio al messaggio successivo (o revisionando quelli vecchi).

Riferimenti

MSDN – https://msdn.microsoft.com/en-us/library/windows/desktop/dn742471(v=vs.85).aspx

Apple – https://developer.apple.com/library/mac/documentation/UserExperience/Conceptual/OSXHIGuidelines/WindowAlerts.html

 

Il club delle 6

“Perché non si iscrive al ‘Club delle sei’?”

“Il ‘Club delle sei’?” chiese un po’ sconcertato.

“Caro ragazzo”, spiegai, ” Beniamino Franklin afferma che pochissimi tra gli uomini giunti al successo indugiavano tra le coltri al mattino. In base a questo principio io anticipai di un’ora e mezzo la mia sveglia e ciò mi consentì di dedicare un’ora completa alla lettura e allo studio. […]”.

wall_clock_sixQuesto è un estratto preso dal libro Il venditore meraviglioso di Frank Bettger. Ne consiglio la lettura anche se non si è tra gli addetti ai lavori di vendita (nemmeno io lo sono): è ricco di concetti su come trattare (con) le persone che si posso applicare a tutti gli ambiti astraendo i concetti specifici.

Non credete che un’attenta pianificazione e il suo rispetto scrupoloso possano portare a risultati grandiosi? Io penso di sì e credo possa essere applicato a qualsiasi settore: dal personale, allo sportivo, al professionale. Vi dirò di più, credo sia proprio questa la chiave per “concludere le cose” e arrivare a fine giornata sentendosi soddisfatti.

P.S.: il post era doveroso perché questo trafiletto ha dato il via a tutta una serie di meccanismi e pensieri che si sono concretizzati anche con la nascita di questo blog.

Invece di…

Un collega ha comprato qualche settimana fa SQL Server 2014 Unleashed. È uno dei soliti libro-mattone che potresti usare come fermaporte nelle giornate più ventose. Lo sfogliamo casualmente durante le pause caffè o altre occasioni in cui si stacca dal monitor per prendere fiato. Così mi sono imbattuto nel capitolo dei trigger, in particolare nella sezione degli instead of trigger.

Scopro un mondo parecchio interessante, dei trigger che scattano prima delle effettive operazioni sui dati: a differenza dei trigger tradizionali che scattano ad operazioni eseguite (chiamati trigger AFTER). Nel dettaglio:

  1. Viene recepito un comando DML;
  2. Scatta trigger INSTEAD OF;
  3. Scattano controlli CHECK;
  4. Scatta trigger AFTER.

Esempio:

CREATE TRIGGER dbo.TI_PERSONE_CONTROLLI ON dbo.PERSONE INSTEAD OF INSERT

In un primo momento non ne trovo un’applicazione che potrebbe fare al caso nostro e archivio la questione.

Verso sera capita che abbiamo problemi di spazio su disco presso un cliente. Delle verifiche ci portano a scoprire che una tabella di log è esageratamente grande e popolata erroneamente da un bug di un programma di scambio dati. Il bug era di semplice risoluzione ma per vari motivi era impossibile sostituire il programma nel server. Amari estremi, estremi rimedi:

TRUNCATE TABLE LOG;
CREATE TRIGGER dbo.TI_LOG_ANNULLA_INSERT ON dbo.LOG INSTEAD OF INSERT
AS
BEGIN
	PRINT ''
END;

Il giorno successivo abbiamo sostituito il programma di scambio dati e distrutto il trigger instead of.yes

Riferimenti

MSDN https://msdn.microsoft.com/en-us/library/ms189799.aspx