2011-01-15 14 views
9

Aquí están nuestros requisitos básicos:Ejecutar una versión personalizada de una aplicación Rails

  • Tenemos una aplicación de base de rieles, que está siendo mantenido activamente.
  • Queremos ofrecer una versión personalizada de esta aplicación, dado que:
    • Los servidores deben residir en la premisa de nuestros clientes y funcionar en un dominio diferente.
    • hay una instrumentación de registro específica para su propio monitoreo en el centro de datos.

Para hacer eso, puedo ver varias opciones para alcanzar ese objetivo:

  • rama Git
  • Rails::Engine
  • Rails::Application

La respuesta más obvia sería ser la sucursal de Git, para una total flexibilidad.

Sin embargo, no estoy seguro de si es una buena idea, ya que la base de código se comparte en gran medida y la línea principal tiene muchas más actividades. Ponerse al día con rebase/merge podría ser una molestia adicional.

Queremos desacoplar las versiones original y personalizada en la medida de lo posible. En otras palabras, queremos tener menos conflictos lo más posible entre el original y el personalizado.

Rails::Engine o Rails::Application parecía una idea estrecha (no estoy familiarizado con los carriles de Motores), pero yo no entiendo cómo tener OurApp::Application y OurCustomizedApp::Application en un lugar y cambiar entre ellos a nivel mundial y de forma dinámica.

Probablemente sería bueno tener:

  • personalizados inicializadores, controladores y puntos de vista en un directorio independiente para anular (o parche) el original capacidad
  • para especificar qué aplicación (el original o la personalizada) para arrancar mediante una variable de entorno como RAILS_APP
  • ficheros de configuración independientes, así: config/database.yml ser config/customer1/database.yml
  • capacidad de utilizar la misma deploy.rb de Capistrano (p robably con config/servers.yml y config/customer1/servers.yml a definir las funciones y los PI?)

¿Hay prácticas/convenciones para nuestras necesidades? ¿Algún consejo?

Nuestras aplicaciones se ejecutan en Ruby 1.9.2 + Rails 3.0.3.

ACTUALIZACIÓN

Empezamos como una rama Git. Creamos una tarea de rake para generar un archivo en config/branch que incluye texto como "maestro" o "personalizado", y application.rb lo lee en bootstrap.Las configuraciones como database.yml o servers.yml ahora viven en config/mainline/ o config/customized/, y application.rb las maneja en consecuencia.

config.paths.config.database = "config/#{branch}/database.yml" 

No es perfecto, pero es lo suficientemente bueno por ahora. Actualizaré cuando encontremos una mejor manera de hacer esto.

Respuesta

1

Sé que no es la respuesta precisa que está buscando, pero creo que Git va a ser la menor cantidad de trabajo (y la más fácil de administrar, a largo plazo) sobre personalizar la aplicación y agregar lógica para manejar el archivos de configuración adicionales, modificación de los archivos de implementación y administración de los nuevos archivos css/js/template (potencialmente).

El uso de rebase & merge va a ser mucho menos propenso a errores, y mientras mantenga sus ramas sincronizadas de forma regular, no debería tener ningún problema grave para mantener ambas actualizadas. ¡Después de todo, eso es en lo que Git es bueno! ;)

+0

Hemos terminado con la sucursal de Git y ha estado funcionando bastante bien hasta el momento. ¡Gracias! – kenn

0

Usamos Git para hacerlo con bastante frecuencia.

2

Creo que el mejor enfoque es hacer esto a la vieja usanza.

Primero, agregue una clase singleton a su proyecto (en /lib) llamado algo así como Affiliate. Esta clase debe proporcionar implementaciones predeterminadas (lo que quiera que use su aplicación base) para cualquier parte de la aplicación que se pueda personalizar. En este punto, su aplicación funciona de la misma manera, pero tiene ganchos para permitir la personalización.

En el sitio de su cliente, implementar el mismo código fuente (que se envía como una joya, tal vez?), Sino también desplegar un plugin de Rails que anula Affiliate por lo que su producto único instance método devuelve una subclase personalizada que suministra información o comportamientos específicos de cada cliente .

Editado para agregar: El riesgo con este enfoque es que los desarrolladores inadvertidamente rompen cosas porque solo prueban sus cambios contra el afiliado predeterminado. Debe usar pruebas automáticas e integración continua para detectar esto.

+0

nuestra personalización es relativamente pequeña, pero lo suficientemente grande como para no encajar en una sola clase, y donde permitir la personalización es impredecible desde el punto de vista de la línea principal. La personalización necesita mucha potencia, como los inicializadores personalizados, etc. – kenn

1

Parece que tiene dos requisitos interesantes aquí. Usted pregunta cómo tener dos aplicaciones separadas y cambiar entre ellas dinámicamente. Supongo que desea cohost diferentes 'versiones' de la misma aplicación y hacer que la aplicación cambie a diferentes personalizaciones basadas en el dominio. Sin embargo, esto es muy diferente de decir usar las ramas de Git para implementar dos aplicaciones diferentes.

¿Puede aclarar sus requisitos aquí?

No recomendaría las sucursales de Git como una solución aquí. Yo recomendaría usar motores. Especialmente agrupando su motor en una gema.

Incluya la gema en su proyecto personalizado y luego utilice las formas tradicionales de anular la funcionalidad en un motor. También puede usar los métodos tradicionales para extender el código de Ruby existente para anular la funcionalidad en su gema.

De esta manera puede mantener todas las diferencias establecidas en un proyecto separado. Este proyecto separado también tendrá su propio conjunto de pruebas, etc.

+0

si bien creo que es una buena idea, en general, tener un motor para compartir varias aplicaciones, no estoy seguro de mantenerlo como una joya: nuestra actividad en la aplicación mainline es bastante intensa y crear una joya para cada commit. no seas realista Suena como si la aplicación web se implementa desde gema, no desde git repo. Lo tomaría al revés: la aplicación para la línea principal y el motor/complemento para la personalización, sin embargo, tampoco parece una buena opción. – kenn

Cuestiones relacionadas