mejorar nuestra estrategia de despliegue

12

Tenemos una aplicación de comercio electrónico que desarrollamos en nuestra empresa. Es una aplicación LAMP razonablemente estándar que hemos estado desarrollando durante 3 años. Desarrollamos la aplicación en un dominio de prueba, aquí agregamos nuevas funciones y corregimos errores, etc. Nuestro seguimiento de errores y desarrollo de funciones se gestiona dentro de una solución de subversión alojada (unfuddle.com). A medida que se informan los errores, hacemos estas correcciones en el dominio de prueba y luego confirmamos los cambios en svn cuando estamos contentos de que se haya solucionado el error. Seguimos este mismo procedimiento con la incorporación de nuevas funciones.

Vale la pena señalar la arquitectura general de nuestro sistema y aplicación en nuestros servidores. Cada vez que se desarrolla una nueva característica, implementamos esta actualización en todos los sitios que utilizan nuestra aplicación (siempre un servidor que controlamos). Cada sitio que usa nuestro sistema esencialmente usa exactamente los mismos archivos para el 95% de la base de código. Tenemos un par de carpetas dentro de cada sitio que contienen archivos hechos a medida para ese sitio: archivos css / imágenes, etc. Además de eso, las diferencias entre cada sitio están definidas por varias configuraciones dentro de la base de datos de cada sitio.

Esto pasa a la implementación real en sí. A medida que estamos listos para implementar una actualización de algún tipo, ejecutamos un comando en el servidor en el que se encuentra el sitio de prueba. Esto ejecuta un comando de copia (cp -fru / testsite / / othersite /) y revisa cada vhost force actualizando los archivos según la fecha de modificación. Cada servidor adicional en el que nos hospedamos tiene un vhost al que sincronizamos la base de código de producción y luego repetimos el procedimiento de copia en todos los sitios en ese servidor. Durante este proceso, retiramos los archivos que no queremos que se sobrescriban y los devolvemos cuando se completa la copia. Nuestro script de implementación realiza una serie de otras funciones, como aplicar comandos SQL para modificar cada base de datos, agregar campos / nuevas tablas, etc.

Nos preocupa cada vez más que nuestro proceso no sea lo suficientemente estable, que no tolere fallas y que también sea un poco un método de fuerza bruta. También somos conscientes de que no estamos haciendo el mejor uso de la subversión, ya que tenemos una posición en la que trabajar en una nueva característica nos impediría implementar una corrección de errores importante, ya que no estamos haciendo uso de ramas o etiquetas. También parece incorrecto que tengamos tanta replicación de archivos en nuestros servidores. Tampoco podemos realizar fácilmente una reversión de lo que acabamos de lanzar. Realizamos una diferencia antes de cada lanzamiento para poder obtener una lista de archivos que se cambiarán para saber qué se ha cambiado después, pero el proceso de reversión aún sería problemático. En términos de la base de datos, comencé a buscar en dbdeploy como una posible solución. Sin embargo, lo que realmente queremos es una guía general sobre cómo podemos mejorar nuestra gestión e implementación de archivos. Idealmente, queremos que la administración de archivos esté más estrechamente vinculada a nuestro repositorio para que una implementación / reversión esté más conectada a svn. Algo así como usar el comando de exportación para asegurarse de que los archivos del sitio sean los mismos que los archivos repos. Sin embargo, también sería bueno si la solución también pudiera detener la replicación de archivos en nuestros servidores.

Ignorando nuestros métodos actuales, sería realmente bueno escuchar cómo otras personas abordan el mismo problema.

resumir ...

  • ¿Cuál es la mejor manera de hacer que los archivos en varios servidores permanezcan sincronizados con svn?
  • ¿Cómo debemos evitar la replicación de archivos? enlaces simbólicos / algo más?
  • ¿Cómo debemos estructurar nuestro repositorio para que podamos desarrollar nuevas funciones y corregir las antiguas?
  • ¿Cómo deberíamos desencadenar lanzamientos / retrocesos?

Gracias por adelantado

EDITAR:

Recientemente he leído muchas cosas buenas sobre el uso de Phing y Capistrano para este tipo de tareas. ¿Alguien puede dar más información sobre ellos y lo buenos que serían para este tipo de tarea?

robjmills
fuente

Respuestas:

6

Mi consejo para hacer lanzamientos es tener lanzamientos de funciones y lanzamientos de mantenimiento. Las versiones de funciones serían las versiones que obtienen nuevas características. Estos se agregan a su tronco de subversión. Cuando piensa que estas son características completas, las ramifica en una rama de lanzamiento. Una vez que su proceso de control de calidad esté satisfecho con esta versión, etiquete la versión e implemente el código en sus servidores.

Ahora, cuando obtiene un informe de error, confirma esta corrección en la rama y la transfiere al tronco. Cuando esté satisfecho con la cantidad de errores corregidos, puede etiquetar e implementar una versión de mantenimiento.

Es importante que tenga una rama de su base de código en vivo (o que tenga la capacidad de crear una conociendo la revisión en vivo) que esté separada de su rama de desarrollo, para que pueda implementar correcciones en su código en vivo sin tener que implementar nuevas funciones o código no probado.

Recomendaría usar el sistema de empaquetado nativo de su distribución para implementar un nuevo código. Si tiene un paquete que contiene toda su base de código, sabe que todo su código se ha implementado en una especie de operación atómica, puede ver qué versión está instalada de un vistazo, puede verificar su base de código utilizando la suma de comprobación de sus paquetes. Revertir es solo un caso de instalación de la versión instalada previamente del paquete.

El único obstáculo que puedo ver al implementar esto es que parece tener múltiples copias de la base de código para diferentes clientes que se ejecutan en un solo servidor. Intentaría organizar su código para que todos los clientes ejecuten los mismos archivos y no usen copias. No sé lo fácil que sería para usted, pero reducir la cantidad de copias con las que tiene que lidiar reducirá enormemente su dolor de cabeza.

Supongo que, como mencionó LAMP, está utilizando PHP u otro lenguaje de secuencias de comandos, que no requiere un proceso de compilación. Esto significa que probablemente se esté perdiendo un maravilloso proceso llamado Integración continua. Lo que esto básicamente significa es que su código se está probando continuamente para asegurarse de que todavía esté en un estado liberable. Cada vez que alguien registra un nuevo código, un proceso lo toma y ejecuta el proceso de compilación y prueba. Con un lenguaje compilado, generalmente lo usaría para asegurarse de que el código aún se compila. Con cada idioma, debe aprovechar la oportunidad de ejecutar pruebas unitarias (su código está en unidades comprobables, ¿no?) Y pruebas de integración. Para los sitios web, una buena herramienta para probar las pruebas de integración es Selenium. En nuestras compilaciones de Java, también medimos la cobertura del código y las métricas del código para ver cómo progresamos con el tiempo. El mejor servidor de CI que hemos encontrado para Java es Hudson, pero algo como buildbot podría funcionar mejor para otros idiomas. Puede construir paquetes usando su servidor CI.

David Pashley
fuente
Gracias. Sí, estamos usando PHP. Debo admitir que no estoy muy interesado en la integración continua, por lo que sé, es muy similar a las pruebas unitarias, pero no sé mucho más que eso. Estamos interesados ​​en las pruebas unitarias, pero nuestra base de código todavía tiene mucho código de procedimiento heredado que realmente no se presta para las pruebas unitarias. Sin embargo, algunas ideas interesantes, sería bueno escuchar las ideas que tenga sobre cómo nuestro código podría estar mejor organizado para evitar la replicación.
robjmills
La integración continua es, literalmente, ejecutar pruebas automatizadas en cada registro o cada hora o cada día. Siempre y cuando lo hagas de forma regular y automatizada, eso es más o menos CI.
David Pashley
vi este artículo de hoy sobre el uso de Hudson junto con PHP y Phing - toptopic.wordpress.com/2009/02/26/php-and-hudson
robjmills