Quando il bugfixing diventa eccessivo, se mai?

128

Immagina di creare un video player in JavaScript. Questo video player scorre ripetutamente il video dell'utente utilizzando una funzione ricorsiva e, a causa di ciò, il browser attiverà un too much recursion RangeError in un dato momento.

Probabilmente nessuno userà così tanto la funzionalità del loop. L'applicazione non genererà mai questo errore, nemmeno se l'utente ha lasciato l'applicazione in loop per una settimana, ma esiste ancora. Risolvere il problema richiederà di riprogettare il modo in cui il loop funziona nella tua applicazione, il che richiederà molto tempo. cosa fai? Perché?

  • Correggi il bug

  • Lascia il bug

Non dovresti solo correggere gli errori in cui potrebbero imbattersi le persone? Quando il bugfixing diventa eccessivo, se mai lo fa?

Modifica

Se l'approccio ricorsivo che non causa un bug effettivo è un problema per te, supponi che per ogni volta che il giocatore esegue il loop di un video una variabile venga aumentata di 1 . Dopo 2 cicli 53 questa variabile andrà in overflow e il tuo programma non sarà in grado di gestirlo, creando un'eccezione.

    
posta Tiago Marinho 17.10.2016 - 07:16
fonte

16 risposte

164

Devi essere pragmatico.

Se è improbabile che l'errore si verifichi nel mondo reale e il costo per la correzione è elevato, dubito che molte persone considererebbero un buon uso delle risorse da risolvere. Su questa base direi di lasciarlo ma assicurati che l'hack sia documentato per te o per il tuo successore in pochi mesi (vedi l'ultimo paragrafo).

Detto questo, dovresti utilizzare questo problema come "esperienza di apprendimento" e la prossima volta che esegui il ciclo non usi un ciclo ricorsivo inutilmente.

Inoltre, sii preparato per quel bug report. Sareste stupiti di quanto i buoni utenti finali stiano spingendo contro i confini e scoprendo i difetti. Se diventa un problema per gli utenti finali, dovrai risolverlo - quindi sarai contento di aver documentato l'hack.

    
risposta data 17.10.2016 - 07:36
fonte
80

C'era un bug simile in Windows 95 che causava il crash di computer dopo 49,7 giorni . Si è notato solo alcuni anni dopo il rilascio, dal momento che pochissimi sistemi Win95 sono rimasti così a lungo. Quindi c'è un punto: i bug possono essere resi irrilevanti da altri bug più importanti.

Quello che devi fare è una valutazione del rischio per il programma nel suo complesso e una valutazione dell'impatto per i singoli bug.

  • Questo software si trova su un limite di sicurezza?
  • In tal caso, questo bug può provocare un exploit?
  • Questo software è "mission critical" per gli utenti previsti? (Vedi l'elenco di cose che l'EULA Java vieta di usarlo per )
  • Il bug può causare una perdita di dati? Perdita finanziaria? Perdita di reputazione?
  • Quanto è probabile che si verifichi questo errore? (Hai incluso questo nel tuo scenario)

E così via. Questo riguarda il bug triage , il processo per decidere quali bug correggere. Praticamente tutti i software di spedizione hanno elenchi molto lunghi di bug minori che non sono ancora stati ritenuti abbastanza importanti da risolvere.

    
risposta data 17.10.2016 - 17:40
fonte
33

Le altre risposte sono già molto buone e so che il tuo esempio è solo un esempio, ma voglio sottolineare una parte importante di questo processo che non è stato ancora discusso:

Devi identificare le tue ipotesi e quindi testare quelle ipotesi sui casi d'angolo.

Guardando il tuo esempio, vedo un paio di ipotesi:

  • L'approccio ricorsivo alla fine causerà un errore.
  • Nessuno vedrà questo errore perché i video impiegano troppo tempo a giocare per raggiungere il limite dello stack.

Altre persone hanno discusso la prima ipotesi, ma osservate la seconda ipotesi: cosa succede se il mio video è solo una frazione di secondo lungo?

E certo, forse non è un caso d'uso molto comune. Ma sei veramente sicuro che nessuno caricherà un video molto breve? Supponi che i video abbiano una durata minima e probabilmente non ti sei nemmeno reso conto che stavi assumendo qualcosa! Questa ipotesi potrebbe causare altri bug in altri punti della tua applicazione?

Le ipotesi non identificate sono un'enorme fonte di bug.

Come ho detto, so che il tuo esempio è solo un esempio, ma questo processo di identificazione delle tue ipotesi (che è spesso più difficile di quanto sembri) e quindi pensare alle eccezioni a tali ipotesi è un fattore determinante nel decidere dove spendere il tuo tempo.

Quindi, se ti ritrovi a pensare "Non dovrei dover programmare intorno a questo, dato che non succederà mai" allora dovresti prendere un po 'di tempo per esaminare davvero questa ipotesi. Spesso penserai a casi d'angolo che potrebbero essere più comuni di quanto pensassi in origine.

Detto questo, c'è un punto in cui questo diventa un esercizio di futilità. Probabilmente non ti interessa se la tua applicazione JavaScript funziona perfettamente su una calcolatrice TI-89, quindi spendere una quantità di tempo su quella è solo sprecata.

Le altre risposte lo hanno già trattato, ma trovare una linea tra "questo è importante" e "questa è una perdita di tempo" non è una scienza esatta, e dipende da molti fattori che possono essere completamente diverso da una persona o società a un'altra.

Ma una parte enorme di questo processo è innanzitutto l'identificazione delle ipotesi e quindi il tentativo di riconoscere le eccezioni a tali ipotesi.

    
risposta data 17.10.2016 - 17:32
fonte
13

Ti consiglierei di leggere il seguente articolo:

Affidabilità e minacce: una tassonomia

Tra le altre cose, descrive vari tipi di errori che possono verificarsi nel tuo programma. Quello che hai descritto si chiama un difetto dormiente e in questo documento è descritto in questo modo:

A fault is active when it produces an error, otherwise it is dormant. An active fault is either a) an internal fault that was previously dormant and that has been activated by the computation process or environmental conditions, or b) an external fault. Fault activation is the application of an input (the activation pattern) to a component that causes a dormant fault to become active. Most internal faults cycle between their dormant and active states

Dopo averlo descritto, tutto si riduce a un rapporto costi-benefici. Il costo dovrebbe essere costituito da tre parametri:

  • Con quale frequenza si presenterebbe il problema?
  • Quali sarebbero le conseguenze?
  • Quanto ti infastidisce di persona?

I primi due sono cruciali. Se si tratta di un bug che si manifesterebbe una volta in una luna blu e / o che nessuno si prende cura di esso, o che ha una soluzione perfettamente buona e pratica, allora puoi documentarlo in sicurezza come un problema noto e passare ad altri più impegnativi e più compiti importanti. Tuttavia, se il bug causasse il fallimento di alcune transazioni monetarie, o interrompesse un lungo processo di registrazione, frustrando così l'utente finale, allora devi agire su di esso. Il terzo parametro è qualcosa che sconsiglio vivamente. Nelle parole di Vito Corleone:

It's not personal. It's business.

Se sei un professionista, lascia le emozioni da parte e agisci in modo ottimale. Tuttavia, se l'applicazione che stai scrivendo è un tuo hobby, allora sei emotivamente coinvolto e il terzo parametro è valido come qualsiasi in termini di decidere se correggere un bug o meno.

    
risposta data 17.10.2016 - 09:10
fonte
12

Quel bug rimane sconosciuto fino al giorno in cui qualcuno mette il tuo giocatore sullo schermo di una lobby con una presentazione aziendale 24 ore su 24, 7 giorni su 7. Quindi è ancora un bug.

La risposta a Che cosa fai? è davvero una decisione aziendale, non di tipo ingegneristico:

  • Se il bug ha un impatto solo sull'1% dei tuoi utenti, e il tuo giocatore non ha il supporto per una funzionalità richiesta da un altro 20%, la scelta è ovvia. Documenta il bug, quindi continua.
  • Se il bugfix è presente nell'elenco delle cose da fare, spesso è meglio ripararlo prima di iniziare ad aggiungere nuove funzionalità. Avrai i vantaggi del processo di sviluppo software a zero difetti e non perderai molto tempo da quando è presente nell'elenco.
risposta data 17.10.2016 - 16:34
fonte
5

Soprattutto nelle grandi aziende (o nei grandi progetti) c'è un modo molto pragmatico per stabilire cosa fare.

Se il costo del fixing è maggiore del ritorno che la correzione porterà, mantieni il bug. Viceversa se la correzione restituirà più del suo costo, quindi correggi il bug.

Nel tuo scenario di esempio dipende da quanti utenti ti aspetti di perdere rispetto a quanta persona guadagnerai se sviluppi nuove funzionalità invece di correggere quel costoso bug.

    
risposta data 17.10.2016 - 13:58
fonte
5

tl; dr Ecco perché RESOLVED/WONTFIX è una cosa. Basta non esagerare - il debito tecnico può accumularsi se non stai attento. Si tratta di un problema fondamentale del tuo progetto, che potrebbe causare altri problemi in futuro? Quindi aggiustalo. Altrimenti? Lascia stare fino a quando diventa una priorità (se mai lo fa).

    
risposta data 17.10.2016 - 18:26
fonte
5

Ci sono in realtà tre errori nella situazione che descrivi:

  1. La mancanza di un processo per valutare tutti gli errori registrati (hai registrato l'errore nel tuo ticket / backlog / qualunque sistema tu disponga, giusto?) per determinare se dovrebbe essere corretto o meno. Questa è una decisione di gestione.

  2. La mancanza di competenze nel tuo team che porta all'uso di soluzioni difettose come questa. È urgente fare in modo che ciò venga affrontato per evitare problemi futuri. (Inizia a imparare dai tuoi errori.)

  3. Il problema che il video potrebbe smettere di essere visualizzato dopo molto tempo.

Forse non è necessario correggere i tre errori (3).

    
risposta data 17.10.2016 - 11:56
fonte
4

Ci sono molte risposte qui che discutono valutando il costo del bug che viene risolto invece di lasciarlo. Contengono tutti un buon consiglio, ma vorrei aggiungere che il costo di un bug è spesso sottovalutato, forse molto sottostimato. La ragione è che gli insetti esistenti confondono le acque per lo sviluppo e la manutenzione continui. Fare in modo che i tester tengano traccia di diversi bug "non risoltibili" mentre si naviga nel software cercando di trovare i bug nuovi rendono il loro lavoro più lento e più soggetto a errori. Alcuni bug "non risolveranno" che difficilmente influenzeranno gli utenti finali continueranno a rallentare lo sviluppo e il risultato sarà bugger.

    
risposta data 17.10.2016 - 22:14
fonte
2

Una cosa che ho imparato nei miei anni di programmazione è che un bug tornerà. L'utente finale lo scoprirà sempre e farà rapporto. Se aggiustare il bug o no è "semplicemente" una priorità e una scadenza.

Abbiamo avuto grossi bug (a mio parere importanti) che sono stati decisi contro il fixing in una versione, solo per diventare uno stopper per la prossima release perché l'utente finale ha inciampato su di esso più e più volte. Lo stesso vice versa: siamo stati spinti a correggere un bug in una funzione che nessuno utilizza, ma è stato utile per la gestione.

    
risposta data 18.10.2016 - 09:39
fonte
1

Un post-it sulla scrivania di uno sviluppatore senior sul mio posto di lavoro dice

Does it help anyone?

Penso che sia spesso un buon punto di partenza per la riflessione. Ci sono sempre molte cose da sistemare e migliorare - ma quanto valore stai effettivamente aggiungendo? ... che si tratti di usabilità, affidabilità, manutenibilità, leggibilità, prestazioni ... o qualsiasi altro aspetto.

    
risposta data 18.10.2016 - 00:46
fonte
1

Ci sono tre cose qui:

Principi

Questo è un lato della medaglia. In un certo senso, sento che è bravo a insistere nel correggere bug (o cattive implementazioni, anche se "funzionano"), anche se nessuno lo sta notando.

Consideralo in questo modo: il vero problema non è necessariamente il bug, nel tuo esempio, ma il fatto che un programmatore abbia pensato che fosse una buona idea implementare il ciclo in questo modo, in primo luogo. Era ovvio dal primo momento che questa non era una buona soluzione. Ora ci sono due possibilità:

  • Il programmatore non se n'è accorto. Bene ... un programmatore dovrebbe sviluppare un'intuizione di come funziona il suo codice. Non è come se la ricorsione fosse un concetto molto difficile. Fissando il bug (e sudando attraverso tutto il lavoro aggiuntivo), forse impara qualcosa e lo ricorda, se non altro per evitare il lavoro aggiuntivo in futuro. Se il motivo è che non ha avuto abbastanza tempo, la direzione potrebbe apprendere che i programmatori fanno hanno bisogno di più tempo per creare un codice di qualità superiore.

  • Il programmatore ha notato, ma ha ritenuto che "non fosse un problema". Se questo è lasciato a stare in piedi, allora si sviluppa una cultura del laissez-faire che alla fine porterà a cimici dove fa veramente male. In questo caso particolare, a chi importa. Ma cosa succede se il programmatore sta sviluppando un'applicazione bancaria la prossima volta e decide che una certa costellazione non accadrà mai. Quindi lo fa. Cattivi tempi.

Il pragmatismo

Questo è l'altro lato. Di corso probabilmente, in questo caso particolare, non correggi il bug. Ma attenzione - c'è il pragmatismo, e poi c'è il pragmatismo. Un buon pragmatismo è se trovi una soluzione rapida ma solida, ben fondata per un problema. Ad esempio, si evita di sovradimensionare le cose, ma le cose che si implementano effettivamente sono ancora ben congegnate. Il cattivo pragmatismo è quando si ha qualcosa in comune che funziona "proprio così" e si interromperà alla prima opportunità.

Fail fast, fail hard

In caso di dubbi, fallisci velocemente e fallisci.

Questo significa, tra gli altri, che il tuo codice nota la condizione di errore, non l'ambiente.

In questo esempio, il minimo che puoi fare è farlo in modo che il difficile errore di runtime ("profondità dello stack superata" o qualcosa del genere) non si verifichi, sostituendolo con un'eccezione propria. Ad esempio, potresti avere un contatore globale e decidere arbitrariamente di salvare dopo 1000 video (o qualunque numero sia abbastanza alto da non verificarsi nel normale utilizzo e abbastanza basso da funzionare ancora nella maggior parte dei browser). Quindi dai un'eccezione (che può essere un'eccezione generica, ad esempio RuntimeException in Java o una semplice stringa in JavaScript o Ruby) un messaggio significativo. Non devi andare nella misura in cui puoi creare un nuovo tipo di eccezioni o qualsiasi altra cosa tu faccia nel tuo particolare linguaggio di programmazione.

In questo modo, hai

  • ... ha documentato il problema all'interno del codice.
  • ... ne ha fatto un problema deterministico. conosci che la tua eccezione accadrà. Non sei al capriccio di cambiamenti nella tecnologia del browser sottostante (pensa non solo al browser per PC, ma anche a smartphone, tablet o tecnologia del futuro).
  • ... ha facilitato la correzione quando alla fine è necessario risolverlo. La fonte del problema è indicata dal tuo messaggio, otterrai un significativo ritorno e tutto il resto.
  • ... non hai perso tempo a fare "reale" gestione degli errori (ricorda, non ti aspetti mai che l'errore si verifichi).

La mia convenzione è di precedere tali messaggi di errore con la parola "Paranoia:". Questo è un chiaro segno per me e per tutti gli altri che mai si aspettano che quell'errore si verifichi. Posso separarli chiaramente da "reali" eccezioni. Se ne vedo uno simile in una GUI o in un file di log, so per certo di avere un serio problema - non mi sarei mai aspettato che si verificassero, dopotutto. In questo punto vado in modalità crunch (con una buona possibilità di risolverlo rapidamente e abbastanza facilmente, poiché so esattamente dove si è verificato il problema, salvandomi da un sacco di debugging spuri).

    
risposta data 19.10.2016 - 15:08
fonte
0

Mi vengono in mente tre cose:

Prima , l'impatto di un bug identificato deve essere accuratamente esaminato prima che la decisione di lasciare il bug nel codice possa essere presa in modo responsabile. (Nel tuo esempio ho pensato subito alla perdita di memoria che rappresenta lo stack in continua crescita e che potrebbe rendere il tuo browser più lento e lento con ogni ricorsione.) Questa indagine approfondita spesso richiede più tempo rispetto alla correzione del bug , quindi preferirei risolvere il bug nella maggior parte dei casi.

Secondo , i bug hanno la tendenza ad avere più impatto di quanto si pensi inizialmente. Conosciamo tutti molto bene il codice di lavoro perché questo è il caso "normale". I bug d'altra parte sono una "eccezione". Naturalmente, tutti abbiamo visto molti bug, ma abbiamo visto molto più codice di lavoro nel complesso. Abbiamo quindi più esperienza su come si comporta il codice di lavoro che su come si comporta il codice buggy. Ci sono milioni di libri sul codice di lavoro e su cosa farà in quali situazioni. Non ci sono quasi nulla sul comportamento del codice buggy.

Il motivo è semplice: i bug non sono order ma chaos . Spesso hanno in loro una traccia di ordine (o la mettono al contrario: non distruggono completamente l'ordine), ma la loro natura bacata è una distruzione dell'ordine che il programmatore voleva. Il caos stesso tende a sfidare a essere stimato correttamente. È molto più difficile dire cosa farà un programma con un bug rispetto a quello che farà un programma corretto solo perché non si adatta più ai nostri schemi mentali.

Terzo , il tuo esempio conteneva l'aspetto che la correzione del bug avrebbe significato dover ridisegnare il programma. (Se togli questo aspetto, la risposta è semplice: correggi il bug, non dovrebbe impiegare troppo tempo perché non è necessaria alcuna riprogettazione. Altrimenti :) In tal caso perderei fiducia nel programma nel modo in cui è attualmente progettato. La riprogettazione sarebbe un modo per ripristinare tale fiducia.

Tutto ciò che ho detto , i programmi sono cose che le persone usano, e una caratteristica mancante o un secondo bug davvero ingombrante altrove possono avere priorità sulla correzione del bug. Certo, poi prendi il modo pragmatico e fai prima altre cose. Ma non dimenticare mai che una prima rapida stima dell'impatto di un bug può essere completamente sbagliata.

    
risposta data 19.10.2016 - 15:04
fonte
0

Probabilità bassa / Conseguenze lievi = Correzione bassa priorità

  • Se la probabilità di occorrenza è molto bassa
  • Se le conseguenze dell'occorrenza sono miti
  • Quindi il bug non rappresenta una minaccia, quindi non è una correzione prioritaria.

Ma questo non può diventare una stampella per sviluppatori pigri ...

  • Che cosa significa "molto bassa occorrenza"?
  • Quali "conseguenze lievi" significano anche?

Per affermare che la probabilità di insorgenza è molto bassa e le conseguenze sono lievi, il team di sviluppo deve comprendere il codice, i modelli di utilizzo e la sicurezza.

La maggior parte degli sviluppatori è sorpresa che le cose che inizialmente pensavano non sarebbero mai accadute, in realtà accadono molto

Il nostro sistema educativo non insegna molto bene la probabilità e la logica. La maggior parte delle persone, inclusa la maggior parte degli ingegneri del software, ha una logica infranta e intuizioni di rottura. L'esperienza con i problemi del mondo reale e l'esperienza con simulazioni estese sono l'unico modo che conosco per risolvere questo problema.

Affronta la tua intuizione con i dati del mondo reale

È importante creare diversi registri per poter seguire i modelli di utilizzo. Riempi il codice con le affermazioni di cose che pensi non dovrebbero accadere. Rimarrai sorpreso che lo facciano. In questo modo sarai in grado di confrontare la tua intuizione con dati complessi e perfezionarli.

Il mio esempio di problema lieve e misura di controllo

In un sito di e-commerce ho lavorato molto tempo fa, un altro programmatore ha commesso un errore: in alcune oscure condizioni il sistema ha addebitato al cliente un centesimo in meno rispetto a quello registrato nei log. Ho scoperto il bug perché ho creato dei report per identificare le differenze tra i registri e i saldi dell'account per rendere il sistema di contabilità più resiliente. Non ho mai risolto questo bug perché la differenza era molto piccola. La differenza è stata calcolata giornalmente ed era inferiore a US $ 2,00 mensili. È successo così che stavamo sviluppando un sistema completamente nuovo che in un anno dovrebbe sostituire quello attuale. Non ha senso deviare le risorse dal progetto potenzialmente redditizio per aggiustare qualcosa che costa $ 2,00 mensili e che è stato sottoposto ad una misura di controllo appropriata.

Conclusione

Sì, ci sono bug che non devono essere risolti immediatamente, che non sono abbastanza importanti da ritardare lo sviluppo di nuove funzionalità. Tuttavia il sistema deve avere il controllo dell'ocurenza di questo bug per assicurarsi che sia piccolo perché non possiamo fidarci della nostra intuizione.

    
risposta data 02.11.2016 - 10:08
fonte
-1

Penso che questo stia ponendo la domanda sbagliata dall'inizio.

La domanda non è "dovrei risolvere questo bug o non correggere questo bug". Qualunque sviluppatore ha una quantità limitata di tempo. Quindi la domanda è "qual è la cosa più utile che posso fare in un'ora, o quattro ore o una settimana".

Se correggere quell'errore è la cosa più utile da fare, perché migliora il software di gran lunga la maggior parte delle persone, quindi corregge il bug. Se potessi apportare miglioramenti più grandi altrove, aggiungendo funzionalità che mancano a qualcuno o correggendo un bug più importante, allora fai queste altre cose. E punti bonus extra per tutto ciò che rende il tuo sviluppo futuro più efficiente.

    
risposta data 20.10.2016 - 23:50
fonte
-2

La correzione dei bug è sempre un overkill

Classifichiamo prima bug .

È un errore onesto , ad es. un errore singolo o variabile che sfuggiva ai test? In questo caso, spero che oltre a "risolvere" il problema, abbia scritto anche nuovi test di unità, abbia colto l'occasione per refactoring il codice vicino, dove tutto questo è lavoro utile .

Se, tuttavia, è in realtà un difetto di progettazione come nel tuo caso, dovresti rivalutare il design o, nel peggiore dei casi, disabilitare questa funzione.

Quindi, non provare a solo .

Potresti fare di peggio, naturalmente --- potresti provare la metodologia hack-upon-hack . Il video looping è un hack (cattiva architettura e si nota una rottura). Puoi aggiungere un limite di loop , in modo che dopo N iterazioni (che hai testato sia sotto il limite del browser) il ciclo termini.

Le ramificazioni sono ovvie, ora devi supportare sia il codice danneggiato che il nuovo limite del ciclo.

P.S. mi scuso per la vista estrema.

P.P.S. Una nota sulla terminologia: non è possibile "correggere" un bug. Beh, forse un veterinario potrebbe, ma non andiamo lì ;-). I problemi sono risolti o "risolti", mentre i bug vengono rimossi o aggirati.

    
risposta data 19.10.2016 - 13:46
fonte

Leggi altre domande sui tag