Sta usando Git per l'implementazione di una cattiva pratica?

96

Tendo ad usare Git per distribuire il codice di produzione sul server web. Questo di solito significa che da qualche parte un repository Git principale è ospitato da qualche parte accessibile su ssh , e il server di produzione serve quel repository clonato, mentre limita l'accesso a .git/ e .gitignore . Quando ho bisogno di aggiornarlo, sposto semplicemente il repository del server dal repository principale. Questo ha diversi vantaggi:

  1. Se qualcosa va mai storto, è estremamente semplice eseguire il rollback a una revisione precedente, semplice da controllare.
  2. Se uno qualsiasi dei file del codice sorgente viene modificato, controllandolo con facilità come git status , e se il repository del server è stato modificato, sarà ovvio la prossima volta che provo a tirare.
  3. Significa che esiste un'altra copia del codice sorgente, nel caso si verifichino cose brutte.
  4. L'aggiornamento e il rollback è facile e molto veloce.

Questo potrebbe tuttavia avere alcuni problemi:

  • Se per qualsiasi ragione il server web decide che dovrebbe servire .git/ directory, tutto il codice sorgente era ed è leggibile da tutti. Storicamente, c'erano alcune (grandi) aziende che hanno commesso questo errore. Sto usando .htaccess file per limitare l'accesso, quindi non penso che ci sia alcun pericolo al momento. Forse un test di integrazione che assicura che nessuno possa leggere la cartella .git/ è in ordine?

  • Tutti coloro che ottengono accidentalmente l'accesso in lettura alla cartella ottengono anche l'accesso ad ogni revisione passata del codice sorgente che esisteva in precedenza. Ma non dovrebbe essere molto peggio di avere accesso alla versione attuale. Dopo tutto, quelle revisioni sono obsolete per definizione.

Tutto ciò che ho detto, credo che l'utilizzo di Git per la distribuzione del codice in produzione sia ragionevolmente sicuro e molto più semplice di rsync , ftp , o semplicemente copiandolo. Cosa ne pensi?

    
posta Septagram 14.11.2013 - 08:37
fonte

7 risposte

68

Mi spingerei a considerare l'utilizzo di git per l'implementazione di ottime pratiche .

I due problemi che hai elencato hanno ben poco a che fare con l'uso di git per la distribuzione stessa. Sostituisci .git/ per il file di configurazione contenente le password del database e hai lo stesso problema. Se ho accesso in lettura alla tua web root, ho accesso in lettura a tutto ciò che è contenuto in esso. Questo è un problema di hardening del server che devi discutere con l'amministrazione del tuo sistema.

git offre alcuni vantaggi molto interessanti quando si tratta di sicurezza.

  1. È possibile imporre un sistema per la distribuzione in produzione. Mi piacerebbe anche configurare un hook post-receive da distribuire automaticamente in produzione ogni volta che viene eseguito un commit su master . Presumo, naturalmente, un flusso di lavoro simile a git flow .

  2. git rende estremamente facile il rollback del codice distribuito in produzione a una versione precedente se viene sollevato un problema di sicurezza. Questo può essere utile per bloccare l'accesso a problemi di sicurezza di importanza critica che è necessario del tempo per correggere correttamente.

  3. Puoi applicare un sistema in cui i tuoi sviluppatori devono firmare i commit che fanno. Questo può aiutare a rintracciare chi ha implementato cosa produrre se viene rilevato un errore di sicurezza intenzionale.

risposta data 14.11.2013 - 13:21
fonte
24

Non c'è niente di sbagliato nella distribuzione da un repository git, infatti è una pratica abbastanza comune e come si dice molto meno incline agli errori rispetto alla copia dei file su ftp o rsync.

Viste le informazioni che hai fornito, osserverei i seguenti punti:

  • Non limitarti a inserire l'ultimo master. La produzione dovrebbe essere distribuita da un tag di rilascio. Utilizza git flow o simile per ottenere un po 'più di elaborazione attorno alla distribuzione del codice e creazione dei tag. Poiché i tag sono un riferimento immutabile al tuo codice in un determinato momento, sono più stabili rispetto a un ramo principale che potrebbe essere aggiornato da un commit errato.

  • Per quanto riguarda la pubblicazione della directory .git, questo non dovrebbe essere un grosso problema. Basta reindirizzare qualsiasi cosa con prefisso .git a 404 in .htaccess.

  • L'autenticazione git deve essere basata su ssh key, quindi non è necessario memorizzare alcuna password per il repository sul server.

Evita i flussi di lavoro di distribuzione di git!

    
risposta data 19.11.2013 - 14:27
fonte
7

Puoi usare l'argomento --separate-git-dir=<git dir> quando chiami clone git . Questo posizionerà un link simbolico nella directory .git (simbolico a Git, non penso che sia un collegamento simbolico al tuo sistema operativo), e puoi specificare <git dir> in qualche parte al di fuori della radice del documento.

    
risposta data 20.11.2013 - 19:56
fonte
5

Un approccio alternativo che ho preso prima è qualcosa di simile al commento di Terry Chia riguardo i ganci post-ricezione.

Git ha un numero di hook che può essere utilizzato per eseguire tutti i tipi di attività prima / durante / dopo molteplici azioni.

Crea un repository nuda in un punto diverso dalla tua cartella web. Il repository nudo può quindi essere utilizzato come un remoto da inviare a e un hook di post-ricezione può essere attivato per controlla il nuovo codice in una directory specificata.

Questo approccio presenta alcuni vantaggi: la posizione di implementazione agisce come una strada "a senso unico" in cui il codice deve passare attraverso il controllo del codice sorgente per finire nella produzione. È possibile distribuire diversi rami / versioni in posizioni diverse (tutti dallo stesso repository nudo). Fornisce anche un modo semplice per eseguire il rollback utilizzando il checkout git standard. Tuttavia, un avvertimento / conseguenza di questo è che le modifiche al codice sul server non si riflettono in git (i repository nudi non hanno directory di lavoro) quindi dovresti eseguire manualmente git --work-tree=/path/to/code status per vedere eventuali modifiche (ma non dovresti Cambierò comunque il codice di produzione, giusto?)

    
risposta data 29.03.2016 - 17:02
fonte
4

Non sono d'accordo con l'opinione popolare qui. Git è per il controllo della versione, non è per la distribuzione / CI.

I metodi che le persone sostengono qui vanno bene per piccoli progetti, ma in generale, non scalano molto bene.

... che non vuol dire che non devi continuare a fare quello che stai facendo. Tieni presente, man mano che la tua carriera progredisce, che i progetti su cui stai lavorando probabilmente supereranno un flusso di lavoro di distribuzione puramente git.

Il principale cambiamento nel paradigma è smettere di pensare alla distribuzione di rami e iniziare a pensare alla distribuzione dei risultati di costruzione e all'iniezione delle dipendenze ambientali per disaccoppiare l'infrastruttura dalla strategia di ramificazione.

Ad esempio, per utilizzare il paradigma precedente su "distribuzione di file" e rollback. Se avevi distribuito i file, è possibile conservare più versioni dell'applicazione sul server di produzione e, se è necessario eseguire il rollback, è possibile indirizzare il server Web a una versione precedente re-symlinking della web root. Due comandi di shell, microsecondi di inattività, meno spazio per errori rispetto all'utilizzo di git.

Un altro esempio: hai il ramo dev standard > staging branch > flusso di lavoro principale, con un server per ciascuno. Hai cose pronte per andare in dev, ma alcune altre cose sulla gestione temporanea falliscono il controllo qualità. Quindi è necessario eseguire alcune operazioni brutte: rimuovere i cattivi commit dallo stage, ridistribuire lo stage e anche eliminare o correggere i commit errati durante lo sviluppo e sperare che lo sviluppo e la messa in scena non finiscano fuori sincrono.

Invece, se tagliate un ramo di uscita fuori dal master, unite le cose che sono pronte per entrare nel ramo di rilascio e create il risultato, trasformate un server di test su AWS e distribuite il risultato su di esso, eseguite il vostro QA e test funzionali contro quel server temporaneo di gestione temporanea, quindi ha inviato lo stesso risultato al cluster di produzione e lo ha implementato? Quindi rimuovere le autorizzazioni dalla casella temporanea di gestione temporanea attivata, unire la versione in master e contrassegnare il master con un numero di versione.

Ovviamente quelli sono esempi estremi. Di solito, non è così pulito, anche se lo vogliamo, probabilmente è necessario eseguire alcuni processi di compilazione nell'ambiente di destinazione perché sono necessarie modifiche al database. E se hai mods di database non idempotenti tra le versioni, beh, il rollback non sarà così facile, non importa quale sia il metodo che usi, perché devi eseguire il rollback del db (in generale, prova a distribuire il database idempotente cambia, quindi rimuovi i bit del database obsoleti in una versione successiva, dopo che sei sicuro che siano fuori dal flusso dell'applicazione).

Ad ogni modo, immagino che cosa sto ottenendo, è che la mia risposta a "Sta usando git per l'implementazione di cattive pratiche?" è, in generale, "Sì", nello stesso modo in cui l'utilizzo di rotelle di allenamento è dannoso per la guida in bicicletta. È un miglioramento rispetto a spaccare ripetutamente il tuo culo sul cemento, ma alla fine spererai di superarlo.

    
risposta data 24.08.2018 - 18:29
fonte
3

Sono d'accordo con Terry Chia che è una buona pratica. Garantisce:

  • che la revisione sul posto è quella giusta,
  • con tutti i file necessari e controlla la completezza della versione,
  • rendere la procedura di distribuzione facile e veloce

Ma devo aggiungere che ci sono avvertenze che mi sembra di condividere.

Di solito, in un repository git, inserisci:

  • codice,
  • docs,
  • test delle unità,
  • script di implementazione,
  • strumenti di integrazione,
  • .deb archives,
  • sql patch
  • o cose del genere, e forse un mucchio di altre cose

Bene, in produzione vuoi solo il codice!

Perché documenti, test di unità, strumenti o archivi .deb possono occupare molto spazio su disco e non hanno nulla da fare in produzione.

Con Subversion (prima della versione 1.7) si poteva eseguire il checkout della directory src/ e si hanno tutti i vantaggi. Ma con Subversion > 1.7 e con Git, non puoi farlo.

Un'alternativa sarebbe utilizzare i sottomoduli git per creare questo tipo di architettura: %codice% Ma poi il tuo progetto / test e il codice src del progetto non sarebbero sincronizzati e questo sarebbe davvero un succhiare.

La soluzione sarebbe quindi utilizzare "sparse checkout", vedi: link

Quindi puoi usare git, ma per favore fai attenzione a questi inconvenienti.

    
risposta data 16.09.2016 - 15:04
fonte
1

Ecco lo script che uso per fare git a spingere a prod.

link

Presuppone che qualsiasi cosa spinta al ramo principale sia pronta per la produzione. Tutti gli altri rami spinti vengono ignorati. Puoi modificare questo script di hook in base alle tue esigenze.

Per quanto mi riguarda, metto la mia directory git sotto / var / git e i miei file di produzione da qualche altra parte (come / var / www) e limitano l'accesso a queste directory.

Potresti anche avere il tuo repository git su un server separato dal tuo server di produzione e quindi usare qualcosa come scp e ssh nello script sopra per spostare i tuoi file dal server git al server di produzione. Questo ti permetterebbe comunque di usare git per spingere ai pungoli mantenendo il tuo codice separato dalla tua produzione.

    
risposta data 14.11.2014 - 23:18
fonte

Leggi altre domande sui tag