Forking vs. Branching in GitHub


278

Mi piacerebbe saperne di più sui vantaggi e gli svantaggi del fork di un progetto github rispetto alla creazione di un ramo di un progetto github.

Forking rende la mia versione del progetto più isolata rispetto a quella originale perché non devo essere nell'elenco dei collaboratori del progetto originale. Dal momento che stiamo sviluppando un progetto in casa, non ci sono problemi ad aggiungere persone come collaboratori. Tuttavia, vorremmo capire se il fork di un progetto comporterebbe di più la fusione delle modifiche al progetto principale. Cioè, mi chiedo se le ramificazioni rendono più facile la sincronizzazione dei due progetti. In altre parole, è più facile unire e spingere le modifiche tra la mia versione del progetto principale e il progetto principale quando mi ramifico?

Risposte:


280

Non è sempre possibile creare una succursale o estrarre una succursale esistente e rinviare ad essa, poiché non si è registrati come collaboratori per quel progetto specifico.

Forking non è altro che un clone sul lato server di GitHub :

  • senza la possibilità di respingere direttamente
  • con funzione di coda fork aggiunta per gestire la richiesta di unione

Mantieni un fork sincronizzato con il progetto originale:

  • aggiungendo il progetto originale come telecomando
  • recuperare regolarmente da quel progetto originale
  • rifare il tuo sviluppo attuale in cima al ramo di interesse che hai aggiornato da quel recupero.

Il rebase ti consente di assicurarti che le tue modifiche siano semplici (nessun conflitto di unione da gestire), rendendo la tua richiesta pull più semplice quando vuoi che il manutentore del progetto originale includa le tue patch nel suo progetto.

L'obiettivo è davvero consentire la collaborazione anche se la partecipazione diretta non è sempre possibile.


Il fatto che tu cloni dalla parte di GitHub significa che ora hai due repository "centrali" ("centrale" come "visibili da diversi collaboratori).
Se puoi aggiungerli direttamente come collaboratore per un progetto, non è necessario gestirne un altro uno con una forchetta.

biforcarsi su GitHub

L'esperienza di unione sarebbe più o meno la stessa, ma con un ulteriore livello di riferimento indiretto (spingere prima sul fork, quindi chiedere un pull, con il rischio di evoluzioni sul repository originale che rende le fusioni di avanzamento rapido non più più avanti) .
Ciò significa che il flusso di lavoro corretto consiste nel git pull --rebase upstream(reimpostare il lavoro in cima ai nuovi commit dall'upstream) e quindi git push --force origin, al fine di riscrivere la cronologia in modo tale che i propri commit siano sempre in cima ai commit dal repository originale (upstream) .

Guarda anche:


3
Stiamo sviluppando un progetto in casa e non ci sono problemi ad aggiungere persone come collaboratori. Ma vorremmo capire se il fork di un progetto renderebbe più difficile la fusione dei cambiamenti con il progetto principale.
riprogrammatore

7
@programmatore: se è possibile aggiungere collaboratori, non è necessario il fork. possono rifarsi localmente, quindi unirsi sul ramo di destinazione e quindi spingere direttamente in un repository centrale, invece di dover gestire due repository centrali (quello originale e il fork). Il rebase sarebbe più o meno lo stesso, ma con un'ulteriore direzione indiretta quando è coinvolto un fork. Ancora: qui non serve. Ho aggiornato la mia risposta.
VonC,

14
Onestamente, anche se non è necessario, è sempre una buona idea avere un repository sacro scrivibile solo per sviluppatori senior, team leader o altre persone "fidate" . Tutti gli altri membri del team dovrebbero lavorare nelle loro forcelle (~ sandbox) e contribuire con le loro modifiche sotto forma di richiesta pull. Dal momento che DVCS lo rende possibile, l'abbiamo adattato come "best practice" e lo abbiamo utilizzato con successo anche nei progetti più piccoli ...
interno

1
@intland, quindi sei più a favore di un "flusso di lavoro di Integration Manager" come descritto in stackoverflow.com/users/6309/vonc?tab=responses allora? Per aver introdotto Git in un grande corp, tendo ad adottare prima un flusso di lavoro centralizzato (più familiare per tutti), prima di passare a un "gestore dell'integrazione".
VonC,

15
Dovremmo chiamare forchette "ramoscelli" poiché sono spezzati da un ramo e sono usati per iniziare un albero completamente nuovo. Solo i miei due centesimi - mi piace il linguaggio arboricolo.
Eric

67

Ecco le differenze di alto livello:

Forking

Professionisti

  • Mantiene i rami separati dall'utente
  • Riduce il disordine nel repository primario
  • Il processo del tuo team riflette il processo del collaboratore esterno

Contro

  • Rende più difficile vedere tutti i rami che sono attivi (o inattivi, del resto)
  • Collaborare in una filiale è più complicato (il proprietario del fork deve aggiungere la persona come collaboratore)
  • Devi comprendere il concetto di più telecomandi in Git
    • Richiede una contabilità mentale aggiuntiva
    • Ciò renderà il flusso di lavoro più difficile per le persone che non sono molto a proprio agio con Git

branching

Professionisti

  • Mantiene tutto il lavoro svolto attorno a un progetto in un unico posto
  • Tutti i collaboratori possono spingere nello stesso ramo per collaborare su di esso
  • C'è solo un telecomando Git da affrontare

Contro

  • I rami che vengono abbandonati possono accumularsi più facilmente
  • Il processo di contributo del tuo team non corrisponde al processo di contributo esterno
  • Devi aggiungere membri del team come collaboratori prima che possano ramificarsi

Cosa si intende per "processo del collaboratore esterno"?
Kars Barendrecht,

1
@KarsBarendrecht Aggiornato per usare il termine "collaboratore esterno". Qualcuno che non dispone delle writeautorizzazioni per il repository.
Aidan Feldman,

45

Ha a che fare con il flusso di lavoro generale di Git. È improbabile che tu possa spingere direttamente nel repository del progetto principale. Non sono sicuro che il repository del progetto GitHub supporti il ​​controllo degli accessi basato su succursali, ad esempio perché non vorresti concedere a nessuno il permesso di spingere nel ramo principale.

Lo schema generale è il seguente:

  • Effettua il fork del repository del progetto originale per avere la tua copia GitHub, a cui ti sarà quindi permesso di inviare le modifiche.
  • Clona il tuo repository GitHub sul tuo computer locale
  • Facoltativamente, aggiungere il repository originale come repository remoto aggiuntivo sul repository locale. Sarai quindi in grado di recuperare direttamente le modifiche pubblicate in quel repository.
  • Apporta le tue modifiche e i tuoi commit a livello locale.
  • Trasmetti le tue modifiche al tuo repository GitHub (dato che generalmente non avrai le autorizzazioni di scrittura direttamente sul repository del progetto).
  • Contatta i manutentori del progetto e chiedi loro di recuperare le modifiche, rivederle / unirle e lasciarle tornare al repository del progetto (se tu e loro lo desiderate).

Senza questo, è abbastanza insolito per i progetti pubblici permettere a chiunque di spingere direttamente i propri impegni.


@RecoJohnson, beh ... non ho usato la parola "pull" nella mia risposta (ma "pull" è effettivamente "fetch" + "unisci" in termini Git). Quale uso di "push" pensi sia sbagliato?
Bruno,

2
@RecoJohnson Tu come contributore spingi sul tuo fork GitHub; i manutentori del progetto traggono il tuo contributo dal fork
mljrg,

1
Penso che il presupposto che è improbabile che ti venga assegnato un collaboratore sia più vero nel mondo dell'open source che in molte organizzazioni con team di sviluppo che ora usano Git dove il team di sviluppo è ben definito. Penso che questa sia una distinzione importante da fare e che non sia abbastanza, probabilmente perché aziende come Gitlab prosperano perché comprendono le esigenze dell'impresa e la necessità di controlli.
code4cause

9

Forking crea un repository completamente nuovo dal repository esistente (semplicemente facendo git clone su gitHub / bitbucket)

Le fork sono utilizzate al meglio: quando l'intento della "divisione" è quello di creare un progetto logicamente indipendente, che potrebbe non riunirsi mai con il suo genitore.

La strategia di filiale crea una nuova filiale sul repository esistente / funzionante

I rami sono meglio usati: quando vengono creati come luoghi temporanei per lavorare attraverso una funzione, con l'intento di unire il ramo con l'origine.

Più specifico: - Nei progetti open source è il proprietario del repository che decide chi può inviare al repository. Tuttavia, l'idea dell'open source è che tutti possono contribuire al progetto.

Questo problema è risolto dalle forcelle: ogni volta che uno sviluppatore vuole cambiare qualcosa in un progetto open source, non clonano direttamente il repository ufficiale. Invece, lo forzano per creare una copia. Quando il lavoro è finito, fanno una richiesta pull in modo che il proprietario del repository possa rivedere le modifiche e decidere se unirle al suo progetto.

Fondamentalmente, il fork è simile al branching delle funzionalità, ma invece di creare branch viene creato un fork del repository e invece di fare una richiesta di unione si crea una richiesta pull.

I collegamenti seguenti forniscono la differenza in modo ben spiegato:

https://blog.gitprime.com/the-definitive-guide-to-forks-and-branches-in-git/

https://buddy.works/blog/5-types-of-git-workflows

http://www.continuousagile.com/unblock/branching.html


Le affermazioni "meglio utilizzate" in questa risposta sembrano ignorare molte delle questioni che impediscono alle ramificazioni di funzionare per cose come i progetti open source, così come la realtà di come le forcelle vengono utilizzate nel mondo reale. È estremamente comune vedere le forcelle utilizzate insieme alle richieste pull per consentire alle persone di collaborare a un progetto che non hanno tutti le autorizzazioni per modificare direttamente un determinato repository.
StriplingWarrior il
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.