Intentando responder a mi pregunta: el uso de git para las fusiones de svn parece prometedor.
Actualización: no es solo prometedor, es un gran éxito. En resumen, Linus was right.
Acabo de completar una gran fusión de 2 ramas svn que han estado separadas durante 1,5 años; Se cambiaron 3k archivos, obtuve toneladas de conflictos en svn (~ 800 creo).
me encontré con git & git-svn un protector de la vida:
- resolución automática de conflictos: para empezar, le dio una gran cantidad de archivos de menos conflictivos (~ medio creo)
- rendimiento increíble
- excelente repo/branching model, flujos de trabajo flexibles: experimentación fácil con diversos enfoques, como la fusión de fragmentos por uno (en tiempo), siempre haciendo comprobaciones de cordura (compilación, etc.); cada vez que se produce un problema: retrocede. Siempre puedes dar un paso atrás cuando sea necesario.
- facilidad de uso, gran utillaje:
git-log
(y las opciones subyacentes git-rev-parse
), nada puede ser más poderoso que esto. También es útil: -p
le ofrece diffs de una sola vez; en svn obtienes un log, luego encuentras el diff para esa "revisión-1: revisión", o usas UI torpes. Buscar cuando se agregó/eliminó una cadena en el repositorio, buscar múltiples ramas simultáneamente
gitk
: muy útil para visualizar historiales de sucursales, combinado con excelentes capacidades de búsqueda. No he visto nada como esto en otras herramientas, especialmente no tan rápido como este.No importa que se encuentra en Tk, es simplemente brillante
git gui
: funciona bien incluso si no la más sexy - gran ayuda para los novatos para descubrir cosas
blame
: un milagro. Sí, detecta que el segmento original proviene de (copia & pasta, etc)
mergetool
: mucha experiencia más agradable que dando inicio a la gran svn merge
que luego se detiene cada vez que (. Es decir, cada 5 minutos) que se ejecuta en un conflicto, pulse ' (p) ostpone ', que busca manualmente los archivos en conflicto más adelante. Prefirió un sabor de esto integrado en git gui
(se necesitaba tiny patch para eso). Se encontraron herramientas integradas de diferenciación externas mejor configurables que en svn
.
- enchufable se fusionan los conductores y control de grano fino de ellos
rebase
permitido para filtrar las partes más sucios de la historia SVN
- distribución: no hay necesidad de ir a la oficina cuando se trabaja en esto, podría hacer una pausa & progreso paso a paso en el tren/avión, etc ..
- una unidad USB con Unison realizado la sincronización de trabajo < -> casa un pedazo de la torta
- esto no haría h ave sido posible sin compresión loca del GIT (antiguo proyecto de 5 años con las confirmaciones, 26k toneladas de ramas y archivos binarios, el tronco svn checkout: 1.9GB => todos ellos en el repositorio git completa: 1,4 GB)
Por lo tanto, esto realmente puede marcar la diferencia de una pesadilla a la alegría, especialmente si le gusta aprender (lo que requiere un poco de esfuerzo en este caso, supongo que aprender una motocicleta después de una bicicleta).
Aunque no puedo obligar a todos en la empresa a cambiar de inmediato, realmente no tenía la intención de hacerlo. Una vez más, nos salva por git-svn
'mojar el dedo del pie ante todo' .. Pero al ver las reacciones de sus colegas el interruptor podría ocurrir mucho antes de que nadie espera :)
Me decir- incluso si nos olvidamos de fusiones & confirmaciones, estas cosas ya es grande como una interfaz de sólo lectura para las consultas, visualización, copias de seguridad, etc ..
Advertencia:
"no dcommit fusión Git se compromete a el repositorio Subversion Subversion no maneja. se fusiona de la misma manera que como Git, y esto causará problemas. Esto significa que debe mantener su Git desarrollo lineal de la historia (es decir, sin la fusión de otras ramas, simplemente cambio de base)." (último párrafo del http://learn.github.com/p/git-svn.html)
Otra excelente fuente es la sección Pro Git book ' Cambiar las ramas activas básicamente dice que la fusión funciona, pero dcommit
solo almacenará el contenido de la fusión, pero el historial se verá comprometido (lo que rompe las fusiones posteriores), por lo que debe soltar la rama de trabajo después de la fusión. sentido después de todo, y en la práctica es fácil evitar las trampas aquí ..en svn, encontré que las personas generalmente no vuelven a fusionarse de todas formas, por lo que esto solo podría ser visto como un paso atrás si vienes del mundo de git en primer lugar.
De todos modos, el compromiso solo funcionó para mí. Lo hice en mi propia rama de trabajo de svn que guardaba solo para esto, así que evité cualquier conflicto extra esa vez. Sin embargo, decidí hacer la fusión final de esta rama de trabajo al tronco svn en svn (después de sincronizar todo en git); --ignore-ancestry
dio los mejores resultados allí.
Actualización: como me enteré más tarde, los últimos pasos anteriores (rama svn adicional y fusión - ignorar ancestros) se evitan fácilmente manteniendo la rama de la que se trata lineal. Como dice Gabe a continuación, merge --squash
solo crea una simple y estúpida confirmación de svn. Sólo cuando esté listo con gran fusión (s) en la rama de mi local (que podría tomar días/semana), yo ahora sólo:
git checkout -b dcommit_helper_for_svnbranch svnbranch
git merge --squash huge_merge_work_with_messy_nonlinear_history
git commit 'nice merge summary' # single parent, straight from the fresh svnbranch
git dcommit
sé que el seguimiento de la fusión no será un gran trabajo desde el lado del SVN hasta que cambiemos completamente No puedo esperar por eso.
ACTUALIZACIÓN: @ Kevin pidió algunos detalles más en todo el proceso de fusión de las ramas SVN .. Hay un montón de artículos, mensajes por ahí, pero como novato he encontrado algunas de las confuso/engañosa de entrada/salida de fecha .. de todos modos, la forma en que lo hago en estos días (por supuesto, pegado con git-svn después de ese asunto de combinación; al igual que algunos colegas recién infectadas) ..
git svn clone -s http://svn/path/to/just-above-trunk # the slowest part, but needed only once ever..you can every single branch from the svn repo since revision #1. 2)
git svn fetch # later, anytime: keep it up to date, talking to svn server to grab new revisions. Again: all branches - and yet it's usually a faster for me than a simple 'svn up' on the trunk:)
# Take a look, sniff around - some optional but handy commands:
git gui & # I usually keep this running, press F5 to refresh
gitk --all # graph showing all branches
gitk my-svn-target-branch svn-branch-to-merge # look at only the branches in question
git checkout -b my-merge-fun my-svn-target-branch # this creates a local branch based on the svn one and switches to it..before you notice :)
# Some handy config, giving more context for conflicts
git config merge.conflictstyle diff3
# The actual merge..
git merge svn-branch-to-merge # the normal case, with managable amount of conflicts
# For the monster merge, this was actually a loop for me: due to the sheer size, I split up the 2 year period into reasonable chunks, eg. ~1 months, tagged those versions ma1..ma25 and mb1..mb25 on each branch using gitk, and then repeated these for all of them
git merge ma1 # through ma25
git merge mb1 # through mb25
# When running into conflicts, just resolve them.. low tech way: keep the wanted parts, then "git add file" but you can
git mergetool # loops through each conflicted file, open your GUI mergetool of choice..when successful, add the file automatically.
git mergetool my-interesting-path # limit scope to that path
realidad preferido para usar Git' Integración integrada de mergetool de GUI (haga clic derecho en el archivo en conflicto). Sin embargo, eso es un poco limitado, así que mira mi pequeño parche arriba, que te permite agregar un guión de shell donde puedes invocar las herramientas de mezcla que prefieras (probé una variedad de ellas a veces en paralelo ya que causaban una cantidad sorprendente de pena ... pero normalmente estoy atascado con kdiff3 ..
Cuando un paso de mezcla va bien (sin conflicto), una combinación de confirmación se realiza automáticamente, de lo contrario, a resolver conflictos a continuación
git commit # am usually doing this in the git gui as well.. again, lightning fast.
la última fase .. Tenga en cuenta que hasta el momento solo teníamos confirmaciones locales, sin hablar con el servidor svn. A menos que hayas utilizado --squares u otros trucos, ahora terminas con un gráfico en el que tu commit de fusión tiene 2 padres: las sugerencias de tu sv n-espejo ramas. Ahora este es el resultado habitual: svn solo puede tomar la historia lineal ... por lo que 'git-svn' lo simplifica simplemente descartando el segundo padre (svn-branch-to-merge en el caso anterior) ... por lo que el seguimiento de fusión real es ido en el lado svn ... pero de lo contrario está bien en este caso.
Si quiere una forma más segura/limpia, aquí es donde entra mi fragmento anterior: simplemente haga la fusión final con --squash. Adaptado el anterior a este flujo:
git checkout -b dcommit_helper_for_svnbranch my-svn-target-branch # another local workbranch.. basically needed as svn branches (as any other remote branch) are read-only
git merge --squash my-merge-fun
git commit 'nice merge summary' # single parent, straight from the fresh svn branch
git dcommit # this will result in a 'svn commit' on the my-svn-target-branch
Vaya, esto se está poniendo demasiado tiempo, parando antes demasiado tarde .. Buena suerte.
¿Por qué no * solo * usando git-svn para todo? –
@ Vi.esto suena como una pregunta separada de alto nivel, puede agregarla como tal: -/La mía era, aproximadamente: "¿presentarías git-svn en un equipo basado en SVN, solo para ayudar con un gran fusión? " – inger
Después de * solo * fusionarse, pueden pensar en comenzar * solo * usándolo ... –