Pregunta

Tengo un sistema en producción que tiene varios servidores en varios roles. Me gustaría probar un nuevo servidor de aplicaciones mediante la implementación en ese servidor específico, sin tener que volver a implementar en cada servidor en producción. ¿Hay alguna manera de pedirle a Capistrano que se implemente en un servidor específico? Idealmente, me gustaría poder ejecutar algo como

cap SERVER=app2.example.com ROLE=app production deploy

si solo quisiera implementarlo en app2.example.com.

¡Gracias!

[actualización] Probé la solución sugerida por wulong ejecutando:

cap HOSTS=app2.server.hostname ROLE=app qa deploy 

pero capistrano parecía estar tratando de ejecutar tareas para otros roles en ese servidor además de las tareas de la aplicación. ¿Quizás necesito actualizar mi versión de cap (estoy ejecutando v2.2.0)?

¿Fue útil?

Solución

Terminé publicando una pregunta en la lista de usuarios de capistrano aquí , y obtuve la siguiente respuesta de Jamis (editado un poco por mí para mayor claridad):


Pruebe la variable de entorno HOSTS:

cap HOSTS=app2.example.com production deploy

Tenga en cuenta que al hacer esto, se tratará a app2 como un rol en cada rol, no solo cualquiera de los roles en los que se declare.

Si lo que quiere es hacer una implementación regular, pero solo actuar en la aplicación2, y solo cuando se declara app2 en su archivo de recetas, puede usar el HOSTFILTER variable en su lugar:

cap HOSTFILTER=app2.example.com production deploy 

[...]

Considere este ejemplo concreto. Supongamos que tu El script define tres servidores, A, B y C. Y define una tarea, "foo", que (por defecto) quiere ejecutarse en A y B, pero no en C. De esta manera:

role :app, "A", "B"
role :web, "C"

task :foo, :roles => :app do
  run "echo hello"
end

Ahora, si haces cap foo , ejecutará el comando echo en A y B.

Si haces cap HOSTS = C foo , ejecutará el comando echo en C, independientemente del parámetro: roles para la tarea.

Si haces cap HOSTFILTER = C foo , no ejecutará el comando echo en todo, porque la intersección de (A B) y (C) es un conjunto vacío. (Ahí no hay hosts en la lista de hosts de foo que coincidan con C.)

Si haces cap HOSTFILTER = A foo , ejecutará el comando echo solo A, porque (A B) intersectado con (A) es (A).

Por último, si haces cap HOSTFILTER = A, B, C foo , se ejecutará el eco comando en A y B (pero no en C), porque (A B) se cruzó con (A B C) es (A B).

Para resumir: HOSTS anula completamente la declaración de hosts o roles de la tarea, y obliga a todo a ejecutarse contra los hosts especificados. El HOSTFILTER, por otro lado, simplemente filtra los hosts existentes. contra la lista dada, eligiendo solo aquellos servidores que ya están en la lista de servidores de tareas.

Otros consejos

Lo siguiente debería funcionar fuera de la caja:

cap HOSTS=app2.example.com ROLE=app deploy

Si desea implementar en > 1 servidor con la misma función:

cap HOSTS=app2.example.com,app3.example.com,app4.example.com ROLE=app deploy

Tengo un problema similar y probé lo siguiente. Funciona:

cap production ROLES=web HOSTS=machine1 stats

Debería poder hacer algo como esto en deploy.rb:

task :production do
  if ENV['SERVER'] && ENV['ROLE']
    role ENV['ROLE'], ENV['SERVER']
  else
    # your full config
  end
end

También puede especificar el parámetro hosts de nivel de tarea de esta manera:

task :ship_artifacts, :hosts => ENV['DEST_HOST']  do

end 
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top