Come ottenere una transizione graduale dal modello di organizzazione "l'unico grande repository VCS per tutti i prodotti" al modello "molti piccoli repository VCS"?


15

È uno scenario comune che la base di codice di un prodotto detenuto da un in alcuni sistemi VCS evolva fino a un punto in cui tale base di codice può essere considerata come contenente diversi prodotti. La suddivisione della base di codice tra più repository VCS, ciascuno dedicato a un singolo prodotto, può sfruttare diversi vantaggi (vedere Vantaggi di avere un prodotto per repository VCS sul modello di repository bloat di seguito). Dal punto di vista tecnico, dividere la base di codice è un passaggio piuttosto semplice poiché la maggior parte dei VCS supporta questa operazione. La divisione potrebbe tuttavia sollevare problemi di ingegneria relativi a test automatizzati, consegna continua, integrazione del servizio o monitoraggio (vedere Problemi sollevati dalla divisione.) Le organizzazioni che intendono eseguire tale scissione devono quindi sapere come eseguire questa transizione nel modo più fluido possibile, cioè senza interrompere la consegna e il monitoraggio della pipeline. Il primo passo di questo è probabilmente quello di comprendere meglio la nozione di progetto e come delineare la divisione in una base di codice monolitica.

Nelle risposte a queste domande, vorrei vedere:

  1. Un tentativo di fornire una definizione operativa di cosa sia un prodotto, che fornisce criteri pratici per delineare effettivamente i prodotti in una base di codice esistente.

  2. Secondo questa definizione operativa, elaborare un piano che esegua effettivamente la divisione. Possiamo ipotizzare semplificando che la base di codice sia elaborata da un completamente automatizzato implementa l' e . Cioè, ogni ramo è convalidato da una suite di test automatizzata implementata nella base di codice corrente e ogni unione in un ramo "magico" genera che vengono testati e distribuiti. (I manufatti del prodotto sono ad esempio tarball di origine, documentazione, pacchetti software binari, immagini Docker , AMI, unikernels.)

  3. Un tale piano è soddisfacente se spiega come aggirare il

Problemi sollevati dalla divisione

  1. In che modo le procedure di test automatizzate si riferiscono al repository monolitico preesistente e ai repository divisi?

  2. In che modo le procedure di distribuzione automatizzata si riferiscono al repository monolitico preesistente e ai repository divisi?

  3. Dove viene archiviato il codice per le stesse procedure di distribuzione automatizzata?

  4. Dove sono le archiviate , il e strategie di ?

  5. Come garantire che uno sviluppatore abbia bisogno solo di una base di codice alla volta (ma possibile utilizza artefatti di altre basi di codice).

  6. Come può uno strumento come git-bisect


Nota marginale: vantaggi di disporre di un prodotto per repository VCS rispetto al modello di repository bloat

Avere diversi piccoli repository che contengono la base di codice per un prodotto specifico presenta i seguenti vantaggi rispetto all'approccio del "bloat repository":

  1. Con un repository bloat è difficile ripristinare una versione quando un prodotto è instabile, poiché la cronologia viene mescolata con quella di altri prodotti.

  2. Con un repository gonfio, è difficile rivedere la cronologia del progetto o pull, con piccoli repository, è più probabile che leggiamo queste informazioni. (Questo potrebbe essere specifico per VCS come git, dove a differenza di svn, non possiamo controllare i sottotitoli!)

  3. Con un repository gonfio, dobbiamo sviluppare molta più danza del ramo quando ci sviluppiamo. Se abbiamo N repository possiamo lavorare in parallelo su N rami, se abbiamo solo 1 repository possiamo lavorare solo su un ramo o avere un carico di copie funzionanti che sono anche una seccatura da gestire.

  4. Con diversi piccoli repository, i registri forniscono una mappa di calore del progetto. Possono anche essere usati come proxy della diffusione della conoscenza nel team di sviluppo: se non mi impegno in repo X da 3 mesi, potrebbe essere utile assegnarmi in un team che lavora su repo X in modo da essere consapevole degli sviluppi in quel componente.

  5. Con piccoli repository, è più semplice ottenere una panoramica chiara di un componente. Se tutto va in un unico grande repository, non vi è alcun artefatto tangibile che delinea ogni componente e la base di codice può spostarsi facilmente verso la grande sfera di fango .

  6. Piccoli repository ci obbligano a lavorare sulle interfacce tra i componenti. Ma poiché vogliamo avere una buona capsulazione, questo è un lavoro che dovremmo fare comunque, quindi lo considero un vantaggio per i piccoli repository.

  7. Con diversi piccoli repository, è più facile avere diversi proprietari di prodotti.

  8. Con diversi piccoli repository, è più semplice avere standard di codice semplici che sono pertinenti a un repository completo e che possono essere verificati automaticamente.


1
Una parte fondamentale di tale soluzione è un repository di artefatti decente (ad es. Artefatto), che consente di disaccoppiare i componenti dipendenti dallo stesso repository. IOW invece di condividere il codice (un repository), pubblica e utilizza librerie costruite (artefatti). È anche un buon posto per iniziare un tale sforzo, perché puoi refactoring / estrarre i tuoi moduli uno per uno.
Assaf Lavie

Lo è sicuramente. :)
Michael Le Barbier Grünewald

1
Al momento stiamo esaminando un problema molto simile al lavoro. L'approccio che stiamo prendendo in considerazione è di avere un repository principale senza codice impegnato e altri repository collegati come sottomoduli. Ma dobbiamo ancora capire i giusti strumenti e l'integrazione del processo per farlo. Comporrò una risposta dettagliata quando scopriremo i dettagli.
Jiri Klouda

1
Le cose possono diventare un po 'più complicate se i prodotti condividono il codice (indipendente dalla piattaforma / del prodotto). O se esiste un codice comune per famiglia di prodotti. Non che la divisione non sarebbe una buona idea, solo la gestione delle parti e l'elenco dei vantaggi e degli svantaggi sarebbero in qualche modo diversi.
Dan Cornilescu,

2
Penso che al tuo sesto proiettile con git-bisect manchi qualcosa. Mi chiedo se questo non debba essere suddiviso in domande separate in quanto richiede più o meno un libro. Poiché la definizione di un prodotto è altamente soggettiva (e può variare), penso che in realtà sia un livello da poco ad alto per una domanda su un sito SE. O troppo ampio o troppo basato sull'opinione.
Tensibai,

Risposte:


9

È una domanda affascinante per la quale in realtà potrebbero non esistere risposte reali; Apprezzo il fatto che mentre hai cercato di mantenere la domanda contestualizzata sul VCS, si è naturalmente adattata da sola alla progettazione dell'infrastruttura e alla pianificazione dell'implementazione.

Tuttavia, sembra che molti di noi stiano lavorando a questo tipo di transizione, che può essere eccitante, ma allo stesso tempo così frustrante e doloroso; e vorrei condividere le mie esperienze e opinioni, cercando di non essere pedante, e solo perché potrei non essere un bravo ingegnere, anche non essere noioso.

Design

Infrastruttura e architettura dovrebbero andare insieme per scrivere un software moderno. Strettamente accoppiato, se vuoi. Può sembrare strano usare quelle parole, ma qui non stiamo certamente parlando del codice stesso: voglio dire che devono far parte dello stesso progetto. Quando sono arrivate le nuvole e le persone hanno iniziato a scrivere software per loro, quante persone si sono rese conto che mettendo i mudball lì, sarebbero stati gli stessi mudball in un posto diverso (?) Forse alcune persone lungimiranti potrebbero prevedere che, e probabilmente stanno lavorando negli sviluppatori oggi. Poiché devops è solo una parola d'ordine con così tanti significati diversi per persone diverse, ho visto posti in cui il team devops si sarebbe seduto in ogni incontro di architettura; altri luoghi in cui è solo automazione. Per raggiungere questo tipo di trasformazione, dobbiamo lottare per sederci.

Fiducia

La transizione deve essere isolata, nel senso che deve esistere un taglio coerente della storia, che fornisce la transizione stessa e solo, senza alcun altro cambiamento (dopo diversi mesi di preparazione). Con quale fiducia lo approveremmo e spingere il pulsante rosso?

Voglio dire, il codebase deve cambiare per adattarsi alla nuova struttura VCS e sarà molto difficile mantenerlo unito durante lo sviluppo. (per questo problema potrebbero esserci delle strategie di facilitazione, ne parlerò in seguito in seguito, che possono aiutare a parallelizzare un po 'lo sviluppo).

Beh, scommetto che l'unico modo è con i test comportamentali, e la stessa suite di test comportamentali dovrebbe essere lanciata per verificare il vecchio con una nuova base di codice. Non stiamo verificando che l'applicazione si comporti come previsto qui, ma che la transizione non modifichi il comportamento. Avere test falliti può essere una buona cosa! Se continuano a fallire!

In effetti è molto raro che i mudball siano testati bene; di solito il codice è strettamente accoppiato e probabilmente, per la maggior parte del codice legacy, non è stato sviluppato con un approccio guidato dai test, nemmeno con i test unitari.

Se tale codice di prova è assente, deve essere scritto per primo.

Strategia

Sì, la transizione deve essere mantenuta isolata; ma allo stesso tempo integrato. So che qui posso sembrare pazzo, ma non troverei altre parole per descrivere come la fiducia può tenere il passo con gli affari. Pochissime, se non del tutto, le aziende vorrebbero fermare lo sviluppo di una grande base di codice monolitico, per fare spazio a questa transizione, e non lo stiamo realizzando solo nel giro di una moneta. Forse centinaia di sviluppatori potrebbero contribuire continuamente alla base di codice (userei la parola manomissione qui, dal nostro POV). Mentre il nostro lavoro deve indirizzare un'istantanea specifica per fornire fiducia, dobbiamo tenerci ripassati (non in senso inteso qui), per evitare di rimanere indietro per sempre.

La strategia di attuazione qui può offrire esperienze diverse. Una linea comune di sviluppo è quella di avvolgere / adattare (esponendo gli endpoint con schemi facoltativamente riorganizzati) i rami di implementazione più recenti (beh, vivendo in altri repository in questo caso), quando devono interagire con il core. La transizione con una strategia come questa, insieme al refactoring, può allo stesso tempo offrire uno scenario POC per la transizione VCS e, successivamente, un approccio graduale. Vedilo come scolpire la palla di fango. Sì, la vita offre così tante cose più divertenti.

Debito tecnico

Le sfere di gestione aziendale hanno iniziato a comprendere il debito tecnico e tenerlo in considerazione. No, graffio, non è vero. Mentre è sempre più comune raccogliere misurazioni e dati di qualità, in termini di analisi del codice statico, revisione del codice, risultati dei test comportamentali e prestazioni e generare bei report e tutto il resto ... rimane ancora incredibilmente difficile far accettare all'azienda un continuo approccio di refactoring. Il valore commerciale di esso. "Stiamo seguendo un processo agile e questo non porterà alcun miglioramento alle funzionalità, non è vero?" . Fondamentalmente, così facendo stanno negando l'esistenza del debito tecnico. Vedo questo come il necessario passo mancante comune per poter iniziare qualsiasi transizione dal monolito alle architetture di microservizi.

riaggregazione

Dopotutto, potresti comunque voler fornire un'unica vista simile a un repository in cui puoi costruire più di un singolo prodotto. Per qualsiasi motivo, ad esempio curr / next release, multibrand, build del cliente. Strumenti come il repository google potrebbero essere utili in questo caso. Non ne ho mai usato uno da solo, ma so che ne avrò bisogno un giorno.

Test d'integrazione

Con i microservizi, i test di integrazione assumono un contesto diverso, quello di "testare le proprie API". Livelli più alti di test, funzionali o prestazionali, possono e vogliono esistere, ma significano molto senza un adeguato test di integrazione? Sarebbe come avere test di integrazione senza unit test. Ovviamente no. Ecco perché, se devi eseguire il git bisect, lo eseguirai in un ramo del repository di microservizi, dimenticandoti di eseguirlo nel repository mudball.

PS. questa è una bozza, il mio inglese è pessimo e lo risolverò un giorno

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.