git: cómo excluir files de la fusión

Estoy intentando mantener 2 proyectos de website en un repository. Estos sitios web son principalmente los mismos excepto los files de plantilla (html, css) y algunos files de configuration. El sitio principal (que es mi opinión Supersite) está en Branch Master. El segundo sitio está en la twig secondarySite. Cada vez, cuando desarrollo alguna característica nueva en la twig principal, quiero fusionarla en secondarySite, pero quiero excluir la fusión de los files de templates.

Encontré una solución parcial aquí ¿Cómo le digo a Git que siempre select mi versión local para las fusiones conflictivas en un file específico? pero funciona solo cuando cambio el file de plantilla en ambas twigs y se produce un conflicto . Cuando no hay conflictos, solo usa la versión remota más nueva del file.

¿Cómo puedo decirle a git que siempre deje sin cambios los files locales especificados, incluso si no hay conflicto?

¿O tal vez utilizo un enfoque totalmente incorrecto para el problema?

Gracias de antemano por cualquier ayuda.

Como mencioné en mi respuesta sobre los controlleres de combinación , son útiles solo en caso de conflicto.
Esto se aplica a una merge=ours en un file .gitattributes : vea Combinar estrategias .

Una opción muy útil es decirle a Git que no intente fusionar files específicos cuando tienen conflictos , sino que use su lado de la fusión sobre el de otra persona.

Este hilo reciente (2012) lo confirma:

¿Hay alguna manera de fusionar de branchA a branchB y de branchB a branchA mientras se ignoran por completo los cambios en un file que se rastrea y existe en ambas twigs?

No. Fundamentalmente, un object de compromiso en git consiste en un estado de contenido (es decir, un puntero a un object de tree) y un puntero a todo el historial anterior (es decir, cero o más pointers "principales" para asignar objects).
La semántica de un object de confirmación se puede considerar como "He examinado todo el historial en todas las confirmaciones principales, y el estado contenido en mi puntero de tree las reemplaza a todas".

Entonces podría fusionar B en A , pero mantenga la copy del file de A (por ejemplo, usando la estrategia " ours "). Pero eso significa que usted consideró el estado de A y B, y decidió que la versión de A reemplaza lo que sucedió en B Si más tarde deseaba combinar de A a B , la versión del file de B ni siquiera se consideraría como un resultado para la fusión.

Realmente no hay una manera inteligente de evitar esto a través de una estrategia de fusión diferente; es un aspecto fundamental de la estructura de datos de git para almacenar el historial.

Si esas templates están en un subdirectory, es mejor aislarlas en un repository git propio, para include ese repository como un submodule.

De lo contrario, debe revertir los files incorrectamente fusionados antes de la confirmación (como en este hilo ):

 git merge --no-commit other git checkout HEAD XYZ # or 'git rm XYZ' if XYZ does not exist on master git commit 

¿Has intentado usar .gitignore? Detalles disponibles en la documentation de git aquí

Aquí git-update-index – Registra los contenidos de los files en el tree de trabajo al índice.

 git update-index --assume-unchanged <PATH_OF_THE_FILE> 

Ejemplo:-

git update-index --assume-unchanged somelocation/pom.xml

o

Agregar routes de files en .gitignore

¿O tal vez utilizo un enfoque totalmente incorrecto para el problema?

Estás usando un enfoque totalmente equivocado para este problema 🙂

El problema es que las twigs y las herramientas a su alnetworkingedor están destinadas a mantener versiones diferentes de la misma cosa subyacente.

Pero sus dos sitios web no son en realidad la misma cosa subyacente, son dos cosas diferentes con algo en común, y usted tiene que abusar de git porque le miente sobre su relación.

Tus mejores opciones son:

  1. haga que su repository represente el universo de todos (ok, ambos) sitios . Entonces, ambos son visibles en la misma estructura de directory y usan diferentes nombres de ruta. Podrían tener twigs separadas de desarrollo y liberación, pero es opcional. Si los dos sitios tienen algo en común, esto solo puede ser en forma de files compartidos.

    p.ej.

     repo/supersite repo/secondsite repo/common 
  2. haga un repository por separado para cada sitio y duplique los files comunes. Puedes copyr los cambios

  3. haga un repository por separado para cada sitio, y un tercer repository para las cosas en común, y use submodules para combinar superávit + común en un lugar, y segundo lugar + común en otro.

    p.ej.

     super-repo/site # super site content super-repo/common # common repo as submodule second-repo/site # second site content second-repo/common # same common repo as submodule 

    Tenga en count que los submodules se refieren al mismo repository, pero cada instancia puede estar actualmente en una twig diferente o comprometerse

Hasta cierto punto, la elección correcta depende de cuánto cambian los dos sitios de forma independiente, y con qué frecuencia cambian los bits compartidos, y si está bien obligar a ambos sitios a usar la misma versión de los bits compartidos, y qué fracción del contenido total es compartido vs. único, etc. etc.

En cada una de sus twigs, agregue el file .gitattributes en la raíz.

Para cada sucursal, especificó los files que se ignorarán en la fusión de esta manera:

 filename merge=ours 

y no te olvides de activar el controller para eso:

 git config --global merge.ours.driver true 

Intente fusionar, verá que los files especificados en .gitattributes en cada una de las twigs permanecerán intactos durante la fusión.