Come riparare un progetto praticamente senza struttura?


25

Ho lavorato su un progetto software per lo più da solo per oltre 5 anni. All'inizio era un disastro (sono il terzo o il quarto sviluppatore a lavorarci su), e sebbene sia meno un disastro ora è ancora incredibilmente disorganizzato. Il tasso di progresso nel metterlo sotto controllo è glaciale e sto iniziando a sentirmi scoraggiato dallo stato in cui si trova. Come posso davvero iniziare a risolverlo?

Specifiche del progetto: è un programma di vendita scritto quasi interamente in Visual Basic Classic (VB6) con un back-end MySQL e un motore di reporting scritto in C #. Il modulo di reporting C # è una gioia su cui lavorare, è stato scritto solo negli ultimi due anni e prima che tutti i report fossero stati eseguiti in Crystal Reports 9 (sì, abbiamo ancora alcuni report che si basano su di esso).

Il programma vero e proprio, tuttavia, è un disastro completo. Non ci sono 90k LOC totali e circa 10k righe di commenti (per lo più non documentazione, ma vecchio codice che è stato commentato). 158 file di moduli e 80 file di moduli. Non ho idea di quanti di questi siano effettivamente utilizzati, perché alcune funzionalità del programma sono semplicemente deprecate e (a volte) annotate come tali senza che il codice associato sia stato rimosso dal programma. Immagino che solo il 50% del codice sia in uso produttivo effettivo.

Ho paura di toccare molto del codice solo perché non sono sicuro che stia rompendo qualcosa su cui fa affidamento un oscuro cliente, è accaduto in più occasioni di quante io possa contare. È come se ci fossero mine antiuomo sparse in tutto il codice.

Non esiste davvero alcuna struttura per il progetto. Non è orientato agli oggetti, tranne nei pochi posti in cui ho avuto la pazienza di riformarmi finora. Se è necessario ottenere dati su un modulo, si crea un'istanza di un oggetto di database, si dichiara la query proprio lì nella funzione, si esegue e si fa ciò che si desidera con il set di dati.

Quando ho iniziato a lavorare al progetto non c'era alcun controllo del codice sorgente in uso. Ho cercato di incoraggiare le altre persone a cui stavo lavorando per usarlo, ma ero il nuovo ragazzo e i miei tentativi di convincere le persone a usare la sovversione sono falliti. Lo sviluppatore principale dell'azienda ha finalmente rilevato un bug mercuriale negli ultimi due anni e si è assicurato che tutti gli sviluppatori utilizzino il controllo del codice sorgente su tutti i progetti ora, quindi almeno questo è un progresso.

Penso che se fossi in grado di lavorare sulla riforma del progetto a tempo pieno, sarei in grado di fare progressi decenti e forse anche di avere una stima di quanto tempo ci vorrebbe per rifare completamente il progetto, ma è in uso attivo e lo sono viene costantemente chiesto di spegnere gli incendi, correggere bug, aggiungere funzionalità, ecc. ecc.

Quindi, come posso iniziare a risolvere davvero questo progetto? Prova a utilizzare lo strumento VB6 con un'altra lingua? Prova a riscrivere il programma nel mio tempo libero? O è completamente senza speranza?

Aggiornare

Dopo questo post sono tornato al progetto con rinnovato zelo, ma sono tornato alla disperazione entro pochi mesi dopo aver visto un ritmo così lento di progressi. Ho quindi ripetuto questo ciclo altre 2 o 3 volte nel corso del prossimo anno.

Da allora sono passato a un lavoro diverso. Anche se dopo tanti anni di vb6, e solo l'esperienza periferica con altre tecnologie, la ricerca è stata difficile e ho affrontato molti rifiuti lungo il percorso (circa una dozzina di interviste nel corso di un anno). Il mio consiglio agli altri in questa situazione è di considerare di partire per questo fattore da solo. Considera il danno che puoi arrecare alla tua carriera rimanendo in una posizione senza uscita come questa.


4
Sembra piuttosto male. Un inizio sarebbe salvare una copia del codice corrente e rimuovere il vecchio codice che è stato commentato (è solo rumore). Quando lavoravo su un sistema legacy di solito inserivo una data in cima al codice che commentavo. Quindi fai fuori il codice commentato che aveva 6 mesi o più.
programmatore

4
Comincerei con Jamison e mi muoverei giù per lo scaffale. . .
Wyatt Barnett,

1
Hai mai provato a rilevare un progetto C # scritto da un programmatore VB?
שינתיא אבישגנת,

Risposte:


28

Ora che è nel controllo del codice sorgente, puoi eliminare il codice commentato.

Ho iniziato qui in una situazione simile (app 80KLOC VB6 senza controllo del codice sorgente, nessuna struttura reale, quasi tutto fatto nei gestori di eventi).

In circa 2 anni, sono stato convertito più della metà in C # (di solito quando sono richieste nuove funzionalità significative). Tutti i nuovi codici C # hanno una copertura di test unitari. Ci vuole sicuramente molto più tempo per convertire in C # però. Se non aggiungi nuovi moduli significativi, non seguirei questa strada.

Una cosa che ho fatto è stata creare un livello di accesso ai dati rudimentale che si è generato automaticamente dal database. Questo almeno ha riscontrato problemi in cui il nome di una colonna della tabella è cambiato e non ho trovato tutti i posti nel codice. Inoltre, ho lentamente spostato la logica di business in moduli, fuori dai gestori di eventi del modulo.

Tuttavia, ho avuto il vantaggio che l'applicazione era solo interna. Dal momento che avevo un solo sito in cui implementare, potevo correre alcuni rischi più grandi di te. Se ho fatto un errore, di solito non è stato un grosso problema ripararlo. Sembra che tu non abbia quel lusso.

Penso davvero che la tua scommessa migliore sia quella di adottare il seguente approccio:

  1. Impara ogni dettaglio in modo lancinante. Ciò rende meno probabile la rottura involontaria di qualcosa.
  2. Rifattorizza senza pietà per migliorare la separazione e la struttura, ma non provare a mettere in piedi una nuova metodologia come la programmazione orientata agli oggetti, poiché VB6 fa solo schifo.
  3. Trattalo come un'esperienza di apprendimento. Come sapresti che un modo diverso è meglio se non avessi mai visto il modo inferiore?
  4. Non preoccuparti di riscrivere in una nuova lingua / framework / piattaforma a meno che tu non abbia un modulo principale da scrivere. Anche allora, considera attentamente.

Ricorda, l'obiettivo del programma è quello di essere un prodotto che fa guadagnare soldi alla tua azienda. Non deve essere un'opera d'arte impeccabile (e sono un perfezionista, quindi è davvero difficile per me ammetterlo). A volte è meglio abbracciare il pragmatismo.

Presumibilmente ci sono molti programmatori COBOL là fuori che mantengono enormi quantità di codice legacy. Dubito che stiano tutti lavorando follemente a riscriverlo in una nuova lingua. :)


3
+1 Ottima risposta: tutto ciò che posso aggiungere è essere sicuro di non avere troppe aspettative su te stesso. La manutenzione del codice è lenta rispetto al nuovo sviluppo, al codice legacy, anche al codice più lento e non documentato, non strutturato come hai descritto .... Gli ultimi 5 anni ho lavorato su una varietà di basi di codice risalenti agli anni '80 e misure in milioni SLOC ... Conosco il tuo dolore ...
Mattnz,

+1 ma una funzionalità OO su cui VB6 funziona correttamente è Interfaces. Se riesci a vedere un codice simile copiato e incollato alcune volte, potresti essere in grado di eseguire il refactoring in un'interfaccia, se non in una classe completa.
Mark Hurd,

3

Quello che devi fare è il refactoring. Il refactoring è quasi impossibile in una situazione del genere senza un unit test che ti dà la sicurezza di non aver rotto nulla. Pertanto, inizia con la creazione di unit test. Documentare il comportamento del codice - ma non (solo) su carta, ma in più codici - i test unitari. Dopo aver eseguito i test, puoi iniziare a ristrutturare il codice.


11
Sono stato in questa situazione. Innanzitutto, VB6 ha suite di test unitari pietosi. In secondo luogo, i test unitari richiedono quasi sempre DI ed è davvero difficile in VB6 a causa del suo terribile supporto per la programmazione orientata agli oggetti. Non ho ancora avuto notizie da nessuno che abbia preso un progetto VB6, abbia scritto un sacco di test unitari e abbia fatto un binge di refactoring, anche se è la risposta di borsa che ascolterai sempre per una domanda come questa su Programmers.SE. Sai quanto è doloroso scrivere test unitari per la logica incorporata ovunque nei gestori di eventi Form? Devi refactoring prima di poter scrivere i test!
Scott Whitlock,

Mi piacerebbe aggiungere test unitari al nostro codice, ma non so da dove cominciare. Ho effettuato alcuni test unitari in .net e in altre lingue ma solo da zero, senza mai aggiungere test a un progetto esistente. E nessuno dei test di unità che ho fatto è stato su programmi che utilizzano GUI, in particolare non GUI con un sacco di database e logica aziendale mescolati nei gestori di eventi!
Dylan Nissley,

1
Se il codice non è stato scritto per essere testabile, tutto ciò che dovrete fare è scrivere test unitari che coprono i casi semplici e ovvi e perdere i casi limite che causano il 90% dei difetti. Ci sono stato, ho fatto questo, ho perso molto tempo e fatica (leggi Money). Il miglior approccio consiste nell'assicurare che il codice che si modifica sia facilmente testabile, qualunque cosa ciò significhi nell'ambiente in uso, che non suona come un test unitario.
mattnz,

3

Mi viene in mente una regola del " Debugging " di David Agan : smettere di pensare e guardare. Ti capita di avere a tua disposizione una macchina in grado di elaborare grandi quantità di testo. Usalo per capire con precisione quale codice non è più in uso e rimuovilo senza pietà. Se commetti un errore, ecco a cosa serve il controllo del codice sorgente.

Questa è la parte facile. Quello a cui devi pensare dopo è come mangi un elefante? Un boccone alla volta. Prendi " Refactoring " di Martin Fowler e prendilo funzione per funzione, file per file. Non eliminare completamente qualcosa e riscriverlo da ciò che ritieni siano i requisiti. Lavora come un alpinista, non rimuovendo mai la tua sicurezza precedente fino a quando quella successiva non è a posto.

Hai già avuto abbastanza metafore? Il punto è che se lo prendi lentamente e costantemente, con molti miglioramenti semplici come rinominare o dividere una funzione, puoi migliorare le parti cattive del codice senza distruggere quelle buone che sono state costruite attraverso anni di debug e richieste di funzionalità . Volete che il codice rimanga sempre disponibile. Se è possibile farlo mentre si esegue il porting in un linguaggio più moderno, provalo.


Se non eseguito correttamente, "Porting su un linguaggio moderno" fornirà un "programma VB nella sintassi C #" - Attualmente sta lavorando su un'app C con porting su Java che è in realtà "Cava" non Java - è il peggiore di entrambi e il migliore di nessuno dei due ........ Il porting corretto è in realtà una riscrittura in trascinamento, e come ha scritto Joel, è in cima alla lista delle "cose ​​da non fare".
mattnz,

Buon punto. Ecco perché ho detto "se è possibile". Se non puoi farlo a poco a poco e anche scrivere il codice trasferito in modo idiomatico, non dovresti provare.
Karl Bielefeldt,

3

Odio dirlo, ma andrei con "completamente senza speranza" oltre a continuare semplicemente a fare un ciclo infinito di patch / potenziamento e spero che nulla si rompa. Ho visto troppi progetti VB6 come quello che descrivi e tenta di rifattorarli / riscriverli / rifarli in C # /. NET fallisce terribilmente, spesso con le persone incaricate del tentativo di licenziamento.

Il fatto è che prima o poi sarà necessaria una riscrittura completa da zero. Le versioni VB6 e Windows che lo supportano bene sono in declino. Trovare sviluppatori che conoscono le stranezze di VB6 e che sono disposti a lavorare su programmi come questo sta diventando più raro. I limiti interni di VB6 verranno colpiti da enormi programmi come questo, causando strani errori.

Se c'è un buon consenso e impegno per un totale, approfondito, riprogettare e riscrivere a questo punto, iniziare a lavorare su di esso e delegare la manutenzione in corso a qualcun altro (appaltatori, programmatori junior, qualunque cosa funzioni per te). Se le persone non sono abbastanza convinte per iniziare ancora, aspetta solo che il dolore diventi abbastanza grande o passa a pascoli più verdi.


+1 Hai ragione sul fatto che VB6 abbia perso il supporto nelle moderne versioni di Windows. Prima o poi (probabilmente prima), l'applicazione cesserà semplicemente di funzionare dove è necessario.
Bernard,

1

Alcune buone risposte qui già, vorrei aggiungere una cosa. Invece di provare a riscrivere tutto, forse avrai la possibilità di portare almeno alcuni di quei moduli principalmente da 1: 1 su VB.NET (ovviamente, devi fare molta attenzione durante questa operazione)? Secondo la mia esperienza, tale porting può essere eseguito con uno sforzo ~ 5-10 volte inferiore rispetto al tentativo di ricostruire da zero tutte le funzionalità esistenti. E dopo aver portato esso, allora si può iniziare a refactoring - con tutti gli strumenti disponibili nel mondo .NET, come buoni strumenti di unit test, strumenti automatici di refactoring, vera OOP etc.

Ero stato in una situazione simile, in cui dovevamo migrare un vecchio programma C ++ a 16 bit (150k LOC) nel mondo a 32 bit, dove il framework originale della GUI in uso non era più disponibile. Ci è voluto un po 'di tempo per capire che la riscrittura non era realistica, ma dopo aver deciso di portare quella cosa nel mondo .NET, usando C ++, C ++ / CLI e C #, ci sono voluti solo circa 9 mesi per farlo accadere (con circa 1 dev lavorare a tempo pieno su quel progetto). E non disponevamo di test unitari per la parte della GUI, tutti i test di quelle parti venivano eseguiti manualmente.


0

Sebbene pone molta enfasi sul test unitario della tua applicazione che, sebbene una cosa molto importante da fare, è qualcosa di piuttosto difficile da fare in VB6, Steven McConnell ha scritto un libro eccellente su come affrontare un tale progetto.

Dai un'occhiata:

Steven C. MCCONNELL: lavorare in modo efficace con il codice legacy, seconda edizione. Microsoft Press, giugno 2004.

Fondamentalmente, il suo punto è prenderlo lentamente, un po 'alla volta. Raccomanda inoltre di iniziare a utilizzare tecniche di refactoring che difficilmente rompono qualsiasi cosa, a volte peggiorando un po 'a breve termine, e di iniziare a utilizzare tecniche più avanzate poiché il codice sta diventando più pulito e prevede test unitari per supportarlo.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.