¿Los empujes de git simultáneos son siempre seguros si el segundo empujón solo tiene avances rápidos desde el primer empujón?

Deseo enviar automáticamente confirmaciones en el enlace posterior a la recepción desde un repository central en nuestra LAN a otro repository central en la nube. El repository LAN se crea usando git clone --mirror git@cloud:/path/to/repo o commands equivalentes.

Debido a que los files que se están comprometiendo serán grandes en relación con nuestro ancho de banda ascendente, es muy posible que algo así pueda suceder:

  1. Alice inicia un empuje al repository de LAN.
  2. Bill saca del repository LAN mientras se ejecuta el gancho post-recepción.
    • El repository de LAN está en el medio de presionar al repository de la nube.
    • Esto también significa que el repository local de Bill contiene los compromisos que Alice presionó. Confirmado a través de testings.
  3. Bill inicia un push al repository de LAN.
    • El empuje de Bill es un avance rápido del empuje de Alice, por lo que el repository de LAN lo aceptará.

Cuando se ejecuta el enlace posterior a la recepción para el repository de LAN, se iniciará un segundo empujón desde el repository de LAN al repository de la nube y los dos se ejecutarán simultáneamente.

No estoy preocupado por los objects de Git. El peor de los casos es que ambos empujan todos los objects del empuje de Alicia, pero eso no debería importar hasta donde yo entiendo los aspectos internos de git.

Estoy preocupado por los refs. Supongamos que Alice empuja utilizando una connection mucho más lenta, para que el empuje de Bill termine primero. Supongamos que la pérdida de packages u otra cosa hace que el empuje del gancho desde el repository LAN hasta la nube del empuje de Bill termine antes de que el gancho empuje desde el repository LAN hasta la nube del empuje de Alicia. Si tanto Alice como Bill están presionando la twig principal y el empuje de Bill termina primero, ¿cuál será la reference maestra en el repository de la nube? Quiero que sea la CABEZA de Bill, ya que ese es el último empujón, pero me preocupa que será la CABEZA de Alice.

Más aclaraciones:

Me doy count de que el empuje de Alice desde su máquina al repository de LAN fallará si el empuje de Bill desde su máquina al repository de LAN termina primero. En ese caso, el enganche posterior a la recepción del repository LAN no se ejecutará. Además, suponga que nadie va a realizar forzados, por lo que si el gancho post-recepción se ejecuta en el repository LAN, todos los cambios de ref son rápidos.

Si el empuje de Bill termina primero, el empuje de Alicia fallará porque antes de que los refs se actualicen, git se asegura de que la reference del repos sea la misma que antes. En este escenario, no será así. Alice terminará viendo el post de error y necesita resolver los problemas. Lo mismo aplica para Bill en el caso vice versa. Por lo tanto, en su gancho posterior a la recepción debe asegurarse de que los refs originales y nuevos para el repository sean diferentes ahora. Si no es así, no levante el repository nuevo para ahorrar algo de trabajo.

Todavía veo un problema en su escenario y es con el impulso a la nube. Puede tener el MISMO problema con el gancho empujando dos refs válidos hasta la location de la nube. Excepto que ahora no sabrá si necesita presionar al repository en el script si falla la primera vez porque no sabrá si el ref fallante fue más antiguo o más nuevo que el que se lanzó … especialmente si no fueran simples avances rápidos que pueden suceder de vez en cuando. Si solo forzaste el empuje sin importar lo que tuviese una posibilidad, la nube tendrá una REF VIEJA hasta que otro gancho empuje algo más hacia arriba más tarde. En el caso de Alice, habría fusionado los cambios de la cadena ascendente o de cualquier cantidad de otras soluciones, pero probablemente la secuencia de commands no debería tener esa capacidad de toma de decisiones.

En el gancho, es posible que pueda hacer algo de magia de secuencia de commands en el repository actual para determinar las marcas de time y similares y solo presionar si hay un avance rápido, pero eso parece desorderado y es más probable que se necesite una combinación de todos modos. Creo que una solución mejor que usar un enganche posterior a la recepción es utilizar una tarea cron o progtwigda cada cinco minutos (o la frecuencia que desee) que simplemente ejecute un git pull en la twig principal de su mirror remoto. Si no tiene acceso a ese repository, puede hacer el forzado desde su repository LAN con un trabajo cron en su lugar. Creo que esto es más seguro que el anzuelo y less complicado. Esto le asegurará que la sucursal en la nube de respaldo siempre está en el lugar correcto cada pocos minutos y no se arriesga a presionar a un árbitro más viejo y nunca get el más nuevo hasta que otro usuario lo presione, como lo hace el gancho.

Git 2.4+ (Q2 2015) introducirá impulsos atómicos , lo que facilitará que el server administre el order de empujes.
Vea el trabajo realizado por Stefan Beller ( stefanbeller ) :

  • commit ad35eca t5543-atomic-push.sh: agregue testings básicas para empujes atómicos

Esto agrega testings para la opción de empuje atómico.
Las primeras cuatro testings comtestingn si la opción atómica funciona en buenas condiciones y las últimas tres revisiones comtestingn si la opción atómica evita que se modifique cualquier cambio si solo una reference no se puede actualizar.

  • commit d0e8e09 push.c : agregar un argumento --atomic

     --[no-]atomic 

Use una transacción atómica en el lado remoto si está disponible.
O bien todas las references se actualizan o, por error, no se actualizan las references.
Si el server no admite impulsos atómicos, la inserción fallará.

  • commit 4ff17f1 : send-pack.c: add --atomic argumento de línea de command --atomic

Esto agrega soporte para send-pack para negociar y usar impulsos atómicos si el server lo admite. Los empujones atómicos son activados por una nueva bandera de línea de command --atomic .

  • commit 1b70fe5 : receive-pack.c : negociar soporte de empuje atómico

Esto agrega la opción de protocolo atómico para permitir que receive-pack informe al cliente de que tiene capacidad de empuje atómico .
Esta confirmación hace que la funcionalidad introducida en las confirmaciones anteriores se active para el lado de la publicación.
Los cambios en la documentation reflejan las capacidades de protocolo del server.

  atomic ------ 

Si el server envía la capacidad ' atomic ', es capaz de aceptar impulsos atómicos.
Si el cliente que realiza la request solicita esta capacidad, el server actualizará los refs en una transacción atómica.
O bien todos los refs se actualizan o ninguno.