Stiamo provando a lavorare su una strategia di ramificazione efficace per la nostra organizzazione, in modo che rilasci, versioning e simili vengano gestiti in modo coerente.
Abbiamo molte soluzioni basate su C #, ognuna con un numero qualsiasi di 2-60 progetti. Ogni soluzione si riferisce a un particolare prodotto per il quale pubblichiamo aggiornamenti su base regolare. Questi prodotti hanno una certa interdipendenza, ma non molto. Quando attraversano, per tradizione abbiamo creato un progetto di tipo proxy che fornisce la logica per accedere alla risorsa ai progetti dipendenti.
Ad esempio, abbiamo un sito Web API Web che ha un progetto proxy per astrarre gli endpoint (creare un Web Client, autenticare e effettuare la chiamata all'URL), quindi gli altri progetti devono semplicemente chiamare quel proxy. Questi progetti proxy condividono un numero di versione con il progetto a cui si riferiscono e vengono rilasciati / consumati tramite un feed NuGet interno. Generalmente seguiamo SemVer per aiutare a gestire eventuali modifiche di rottura, con il controllo della versione appropriata sul progetto proxy (ad esempio l'API Web) per garantire che il comportamento funzioni come previsto.
Questa strategia ha funzionato bene per noi, ma sembra che ci sia una caduta che non possiamo superare: il ciclo di rilascio.
In base a Git Flow, abbiamo tagliato% ramo% di% del nostro ramo release
primario per ogni soluzione (rilasciamo contemporaneamente tutti i nostri prodotti contemporaneamente). All'interno di questo ramo, incrementiamo il numero di versione (maggiore / minore in base al tipo di modifiche) e aggiorniamo i pacchetti NuGet interni alla versione più recente. Queste filiali di rilascio si collegano al nostro ambiente QA finale, che è il luogo in cui tutti i prodotti vengono testati insieme per i bachi emergenti e si verifica una segnalazione finale.
Tecnicamente, dovremmo essere in grado di finalizzare tutti i rami di rilascio e distribuire il codice risultante da ciascun ramo principale. Tuttavia, si verificherebbe una mancata corrispondenza della versione tra gli assembly distribuiti e quelli consumati.
Un esempio di chiarezza:
Abbiamo il progetto A, che include un Proxy Project A e non ha dipendenze, e Project B, che consuma il Proxy Project A.
Suppongo che ogni commit, indipendentemente dal ramo, sia costruito con un numero di versione univoco per progetto, e distribuiamo gli assembly creati dal ramo develop
.
- Abbiamo tagliato i nostri due rami
master
:release
(che produceA 1.0.0.001
eA 1.0.0.001
) eA Proxy 1.0.0.001
(che produceB 1.0.0.001
). - Entrambi i progetti ottengono il numero di versione avanzato di un numero di versione secondario:
B 1.0.0.001
eA 1.1.0.002
- Aggiorniamo i pacchetti NuGet per il Progetto B:
B 1.1.0.002
, che ora consumaB 1.1.0.003
- Il test è completato, non sono stati trovati errori, è stata approvata la firma finale. Entrambi i progetti sono uniti a
A 1.1.0.002
:master
eA 1.1.0.003
(consumoB 1.1.0.004
)
Tuttavia, ora c'è una discrepanza nei numeri di versione - abbiamo distribuito A 1.1.0.002
, ma stiamo consumando A 1.1.0.003
. In questo caso, potremmo essere in grado di assumere che questi contengano lo stesso codice esatto e che la differenza nei numeri di versione sia dovuta a un'unione di diramazione, che è vera qui, ma potrebbe non essere sempre.
In passato, il modo in cui abbiamo lavorato attorno a questo era di unire sequenzialmente i rami di rilascio in ordine della catena di dipendenze e aggiornare i progetti dipendenti, ma se un bug viene trovato a monte nel ciclo di rilascio, non abbiamo modo di applicare patch fuori da un ramo A 1.1.0.002
(che non sembra avere senso perché il codice non è tecnicamente ancora implementato - è ancora in fase di test a causa dei prodotti dipendenti, e non è ancora stato completamente disconnesso).
Come possiamo risolvere questo paradosso? Dobbiamo mantenere sincronizzati tutti i cicli di rilascio del prodotto a causa della relazione dipendente tra di loro, ma vogliamo anche garantire che per ogni prodotto e dipendenza siano state rilasciate le versioni che sono state testate e firmate.