Organizando proyectos de Java

Soy un desarrollador junior y recientemente comencé a trabajar para una oficina muy pequeña en la que hacen mucho desarrollo interno. Nunca he trabajado en un proyecto que involucró a más de un desarrollador o era tan grande y complejo como estos.

El problema es que no usan todas las herramientas disponibles (control de versiones, construcción automatizada, continuous integration, etc.) en su totalidad: principalmente un proyecto es un gran proyecto en eclipse / netbeans usando cvs para control de versiones y todo lo que está registrado (incluidos los flasks de la biblioteca), comenzaron a utilizar la ramificación por primera vez cuando comencé a hacer twigs para tareas pequeñas y a fusionarlas. A medida que los proyectos crecen y se vuelven más complejos, comienzan a popup problemas con las dependencies, la estructura del proyecto vinculada a un IDE, la construcción puede ser un PITA a veces, etc. En el mejor de los casos, es agitado.

Lo que quiero es establecer un entorno de desarrollo donde desaparezcan la mayoría de estos problemas y ahorraré time y esfuerzo. Me gustaría configurar proyectos de una manera independiente de IDE que se usa con el control de versiones (estoy inclinado hacia SVN en este momento), evitar problemas de dependencia y automatizar la construcción tanto como sea posible.

Sé que hay múltiples enfoques y herramientas para esto y no quiero ver que se inicie una guerra santa, realmente agradecería las recomendaciones prácticas basadas en la experiencia y lo que ha encontrado que es útil cuando se enfrentan problemas similares. Todos los proyectos son proyectos de Java y abarcan desde aplicaciones web hasta aplicaciones "genéricas", y utilizo Eclipse la mayor parte del time, pero también uso Netbeans si es necesario. Gracias por adelantado.

Pareces estar casi exactamente en el punto donde trabajé en el lugar donde comencé hace 1,5 años, la única diferencia es que has empezado a jugar con las twigs, que en realidad es algo que todavía no hacemos en mi trabajo pero más sobre eso más adelante en esta respuesta.

De todos modos, estás enumerando un muy buen set de herramientas que pueden ayudar a una empresa pequeña y funcionan muy bien como subtemas, así que sin más preámbulos,

Sistemas de control de versiones

La mayoría de las pequeñas empresas actualmente usan CVS o SVN y no hay nada malo en eso, de hecho estaría realmente preocupado si realmente no se utilizara el control de versiones. Sin embargo, tiene que usar el control de versiones correcto , solo tener uno no hará su vida más fácil. Actualmente usamos CVS y estamos estudiando Mercurial , pero descubrimos que lo siguiente funciona como un buen set de convenciones cuando trabajamos con CVS (y sospecho que SVN también):

  • Tener usuarios separados para todos los commiters. Es más que valioso saber quién cometió qué.
  • No permita posts de compromiso vacíos. De hecho, si es posible, configure el repository para rechazar cualquier confirmación sin comentarios y / o comentarios pnetworkingeterminados. La confirmación inicial para FooBarizer es mejor que el post de logging vacío
  • Use tags para marcar hitos, prototypes, alfas, versiones beta, versiones candidatas y versiones finales. No use tags para trabajos experimentales o como notas al pie / notas post-it .
  • No use sucursales ya que realmente no funcionan si continúa desarrollando la aplicación. Esto se debe principalmente a que en CVS y SVN la ramificación simplemente no funciona como se espera y se convierte en un ejercicio inútil mantener más de dos twigs vivas (la cabeza y cualquier twig secundaria ) a lo largo del time.

Recuerde siempre que para la compañía de software el código fuente es su fuente de ingresos y contiene todo el valor de su negocio, así que trátelo de esa manera. Además, si tienes 70 minutos adicionales, realmente recomiendo que veas esta charla que Linus Thorvalds dio en Google sobre git y (d) VCS en general, es realmente perspicaz.

Estructuras automatizadas y entornos de continuous integration

Estos son casi lo mismo en realidad. Las comstackciones diarias son una broma de PR y no se parecen en nada al estado del software real más allá de un rudimentario "¿comstack?" cuestiones. Puede comstackr mucho ruido de código horrible que no hace nada, mantener la calidad del software no tiene nada que ver con la compilation del código.

Por otro lado, las testings unitarias son una gran manera de mantener la calidad del software y puedo decir con orgullo personal que las testings unitarias rigurosas ayudan incluso a los peores progtwigdores a mejorar mucho y detectar errores estúpidos. De hecho, hasta ahora solo ha habido un total de tres errores que el código que he escrito llegó a los entornos de producción y yo diría que en 18 meses es un logro bastante bueno. En nuestro nuevo código de producción usualmente tenemos una cobertura de código de instrucción de + 80%, en su mayoría + 90% y en un caso especial que llega hasta el 98%. Esta parte es un campo muy animado y es mejor que Google para lo siguiente: TDD, BDD, testings unitarias, testings de integración, testings de aceptación, xUnit, objects simulados.

Es un prefacio largo, lo sé. La carne real para todo lo anterior es la siguiente: si quieres tener comstackciones automáticas, haz que sucedan cada vez que alguien se comprometa y asegúrate de que haya una cantidad en constante aumento y mejora de las testings unitarias para el código de producción. Haga que el sistema de continuous integration de su elección (utilizamos Hudson CI ) ejecute todas las testings unitarias relacionadas con el proyecto y solo acepte comstackciones si todas las testings pasan. ¡No hagas ningún compromiso! Si las testings de la unidad muestran que el software está roto, arregle el software.

Además, los sistemas de Integración Continua no son solo para comstackr código, sino que deben usarse para rastrear el estado de las métricas del proyecto de software. Para Hudson CI puedo recomendar todos estos complementos:

  • Estilo de comprobación : comtesting si el código fuente real está escrito de la manera que usted define. Gran parte de la escritura del código que se puede mantener es usar convenciones comunes.
  • Cobertura : codifique las métricas de cobertura, muy útil para ver cómo se desarrolla la cobertura a lo largo del time. Además, mantenerse en línea con la mentalidad de "la fuente es Dios" le permite descartar construcciones si la cobertura cae por debajo de cierto nivel.
  • Explorador de tareas : simple pero dulce: busca tags específicas como BUG, ​​TODO, NOTE, etc. en su código y crea una list para que todos las lean. Manera simple de rastrear notas cortas o errores conocidos que deben solucionarse o lo que sea que se te ocurra.

Estructura del proyecto y gestión de dependencies

Esta es una controversia. Básicamente, todos están de acuerdo en que tener una estructura unificada es excelente, pero dado que hay varios campamentos con diferentes requisitos, hábitos y puntos de vista para emitir, tienden a estar en desacuerdo. Por ejemplo, la gente de Maven realmente cree que solo hay una forma, la de Maven, de hacer las cosas y eso es todo, mientras que los seguidores de Ivy creen que la estructura del proyecto no debería ser golpeada por terceros, solo las dependencies deben gestionarse adecuadamente. y de una manera unificada. Solo que no está claro, nuestra compañía simplemente ama a Ivy.

Entonces, dado que no usamos la estructura del proyecto impuesta por partes externas, voy a contarles un poco sobre cómo llegamos a lo que obtuvimos en nuestra estructura de proyecto actual.

Al principio, usamos proyectos individuales para el software real y testings relacionadas (generalmente denominadas Product y Product_TEST). Esto es muy similar a lo que tiene, un enorme directory para todo con las dependencies como JAR incluidos directamente en el directory. Lo que hicimos fue verificar los proyectos de CVS y luego vincular el proyecto real al proyecto de software de testing en Eclipse como dependencia de time de ejecución. Un poco torpe pero funcionó.

Pronto nos dimos count de que estos pasos extra son completamente inútiles ya que al usar Ant – por cierto, puede invocar tareas Ant directamente en Hudson – podríamos decir al paso de construcción JAR / WAR que ignore todo por cualquier nombre de file (por ejemplo, todo que finaliza con Test o TestCase) o por carpeta de origen. Muy pronto convertimos nuestro proyecto de software para usar una estructura simple, dos carpetas raíz, src y test . No hemos mirado hacia atrás desde entonces. El único debate que tenemos actualmente es si deberíamos permitir que exista una tercera carpeta llamada spikes en nuestra estructura de proyecto estándar y ese no es un debate acalorado.

Esto ha funcionado tremendamente bien y no requiere ningún soporte adicional o complementos de ninguno de los IDEs, lo que es una gran ventaja; la razón número dos que no elegimos. Maven estaba viendo cómo M2Eclipse básicamente se hizo cargo de Eclipse. Y como debe estarse preguntando, la razón número uno para rechazar a Maven fue la torpeza de Maven, una interminable cantidad de largas declaraciones XML para la configuration y la curva de aprendizaje relacionada se consideró un costo demasiado grande en cuanto a lo que obtendríamos de su uso.

Más bien, más tarde, comprometerse con Ivy en lugar de Maven nos ha permitido realizar un cambio sin problemas para hacer algo de desarrollo de Grails que utiliza nombres de carpetas y classs como convenciones para casi todo cuando se estructura la aplicación web.

También una nota final sobre Maven, mientras que dice promover la convención sobre la configuration, si no quieres hacer las cosas exactamente como la estructura de Maven dice que debes hacer las cosas, estás en un mundo de dolor por las razones antes mencionadas. Ciertamente, ese es un efecto secundario esperado de tener convenciones, pero ninguna convención no debería ser definitiva, siempre debe haber al less algún margen para los cambios, flexibilizar las reglas o elegir lo apropiado de un determinado set.

En resumen, mi opinión es que Maven es un bazooka, trabajas en una casa y tu objective final es tenerlo libre de errores. Cada uno de estos es bueno por sí mismo y funciona incluso si eliges dos de ellos, pero los tres juntos simplemente no funcionan.

Ultimas palabras

Mientras tenga less de 10 personas cinputs en el código, tendrá toda la flexibilidad necesaria para tomar decisiones importantes. Cuando vas más allá de eso, tienes que vivir con las elecciones que hayas hecho, sin importar qué tan buenas o malas sean. No solo creas cosas que escuchas en Internet, siéntate y testing todo rigurosamente – diablos, nuestro técnico superior incluso escribió su tesis de licenciatura sobre frameworks web de Java solo para descubrir cuál deberíamos usar, y realmente descifrar lo que realmente necesito. No se comprometa con nada solo porque pueda necesitar algunas de las funcionalidades que brinda en un futuro lejano, elija aquellas cosas que tengan el menor impacto negativo posible para toda la compañía. Al ser la décima persona contratada para la empresa en la que trabajo, puedo suscribir todo en este párrafo con mi propia sangre, actualmente tenemos más de 16 personas trabajando y el cambio de ciertas convenciones en realidad da un poco de miedo en este momento.

Nuestro package de desarrollo (equipo de más de 10 desarrolladores)

  • Eclipse IDE con M2Eclipse y Subclipse / Subversive
  • Subversion para el control de fuente, algunos desarrolladores también usan TortoiseSVN donde falla el Subclipse
  • Maven 2 para la configuration del proyecto (dependencies, complementos de compilation) y liberación de mgmt (labeldo automático de las versiones)
  • Hudson para continuous integration (también crea lanzamientos de instantáneas con files adjuntos e informes de origen)
  • Archiva para repository de artefactos (varios repositorys, por ejemplo, lanzamientos e instantáneas están separados)
  • Sonar para el seguimiento de la calidad del código (por ejemplo, puntos de acceso, cobertura, cumplimiento de las pautas de encoding)
  • JIRA para el seguimiento de errores
  • Confluencia para la wiki del desarrollador y comunicación de documentos técnicos con otros departamentos
  • Docbook para manuales (integrado en la compilation)
  • JMeter para testings de estrés y monitoreo de performance a largo ploop
  • Selenium / WebDriver para testings automatizadas de integración del browser
  • Jetty, Tomcat, Weblogic y Websphere como entornos de testing para aplicaciones web. Los productos se implementan todas las noches y las testings automatizadas se ejecutan en Hudson distribuidos.
  • Lista de correo con todos los desarrolladores para anuncios, correos de información general
  • Reuniones diarias de pie donde todo el mundo count lo que está haciendo actualmente

Esta configuration se considera estándar para nuestra empresa ya que muchos departamentos están usando esas herramientas y hay mucha experiencia y apoyo comunitario para ellas.

Tiene toda la razón al tratar de automatizar tanto como sea posible. Si sus colegas comienzan a ver los beneficios cuando los aspectos de las fases de desarrollo se automatizan, se los alentará a que los mejoren solos. Por supuesto, cada truco de nueva tecnología ("herramienta") es una nueva carga y debe ser gestionado y mantenido. Aquí es donde se mueve el esfuerzo. Ahorras time, por ejemplo, cuando maven realiza automáticamente tus lanzamientos, pero perderás time administrando maven. Mi experiencia es que cada vez que introduje una nueva herramienta (una de las anteriores), toma time ser adoptada y cuidada, pero al final traerá ventajas a todo el equipo cuando se experimente un valor real – esp. en momentos de estrés cuando las herramientas se hacen cargo de la mayor parte del trabajo que tendría que hacer manualmente.

Un fino y admirable instinto. Felicitaciones a usted.

Parte de su problema podría no resolverse usando herramientas. Yo diría que la administración de código fuente necesita algo de trabajo, porque no parece que la bifurcación, el labeldo y la fusión se realicen correctamente. Necesitarás un poco de entrenamiento y comunicación para resolver eso.

No he usado CVS yo mismo, así que no puedo decir qué tan bien apoya esas prácticas. Señalaré que Subversion y Git serían mejores opciones. En el peor de los casos, debería leer el libro de " frijol rojo " de Subversion para get consejos generics sobre cómo administrar el código fuente.

Personalmente, no soy fan de Maven. Creo que es demasiado pesado, especialmente cuando se compara con Ant e Ivy. Yo diría que el uso de aquellos con control de crucero podría ser la solución a muchos de sus problemas.

No mencionaste testings unitarias. Comience a build testings TestNG y Fit en su ciclo de compilation.

Mire en IntelliJ: creo que es un IDE mejor que Eclipse o NetBeans, pero así soy yo.

La mejor de las suertes.

Maven es genial, sin embargo, puede tener una buena curva de aprendizaje, y requiere que el proyecto se ajuste a una estructura de files muy específica. Si tiene un gran proyecto legado, puede ser difícil de mavenizarlo. En ese caso, Ant + Ivy haría lo mismo sin los estrictos requisitos que tiene maven.

Para la automation de compilation, Hudson es más que impresionante. He usado un par de sistemas diferentes, pero es indudablemente el más fácil de configurar y administrar.

Recomiendo usar Maven para build sus proyectos. El uso de Maven otorga valor al proyecto, porque:

  • Maven promueve la convención sobre la configuration, lo que equivale a una buena estructura de proyecto
  • gracias los complementos de Maven facilitan la generación de proyectos para IDE (Eclipse, Netbeans, Idea)
  • maneja todas las dependencies y completa el ciclo de vida de la construcción
  • facilita la modularización de proyectos (a través de proyectos mulitimodulares)
  • ayuda con la carga de versiones / versiones
  • mejorar la calidad del código: fácil integración con serveres de continuous integration y muchos complementos de calidad de código

Maven puede ser un poco desalentador dada su curva inicial de aprendizaje, pero encajaría muy bien con muchas de sus preocupaciones. También te recomiendo que eches un vistazo a Git para el control de versiones.

Para la gestión de proyectos y repositorys, uso trac con subversión .

Esto es lo que estoy usando en este momento, pero probablemente cambie algunas partes (ver el final de esta publicación).

Eclipse como IDE con algunos complementos: JADClipse (para descomstackr .class sobre la marcha, bastante útil), DBViewer para un acceso rápido a la database a través de Eclipse, WTP (Web Tools Platform) integrado en Eclipse para ejecutar Tomcat 6 como server web de desarrollo (bastante rápido), Mylyn (vinculada con el rastreador de errores JIRA ).

Me pregunto acerca de los "proyectos independientes de IDE", en este momento todos estamos apegados a Eclipse: los files de proyectos de Eclipse (.project, .classpath, .settings) están incluso comprometidos en el repository de CVS (para tener un proyecto completamente listo) una vez revisado), pero con Netbeans, con el respaldo de Sun y ejecutándose cada vez más rápido con cada versión (y cada versión nueva de JRE), la pregunta no se cierra.

CVS para el almacenamiento de proyectos, casi sin twigs (solo para parches).

Estoy trabajando en la producción de entornos con Oracle SGBDR, pero estoy usando HSQLDB en mi computadora de desarrollo para hacer testings y build y desarrollar processs mucho más rápido (con la ayuda de la herramienta DDLUtils de código abierto para facilitar la creación de bases de datos y las inyecciones de datos). De lo contrario, uso SQLWorkbench para tareas rápidas de BD (incluida la comparación de esquemas) o el desarrollador de SQL de Oracle (gratuito) para algunas tareas específicas de Oracle (como investating sessions locks, etc.).

Las testings son solo testings de JUnit (ya sean casos de testing unitaria simples o casos de testing más complejos (casi "integraciones"), casi siempre se ejecutan en HSQLDB para correr más rápido.

Mi sistema de compilation es Ant (iniciado desde Eclipse) para varias tareas pequeñas (cargando una guerra en un server remoto, por ejemplo) y (principalmente) Maven 2 para:

  • el process de construcción
  • la publicación de los artefactos lanzados
  • la publicación del website del proyecto (incluidos los informes)
  • lanzar campañas de testings (lanzadas todas las noches)

El front-end de continuous integration es Luntbuild , y el front-end para el repository de Maven es Archiva .

Todo esto funciona Pero estoy bastante decepcionado por algunos elementos de este ecosistema.

Principalmente Maven, es demasiado lento y tengo muchas penas frente a esta herramienta. La resolución de dependencies de conflictos es una broma. Muchas líneas XML en cada POM.xml, networkingundantes en cada proyecto (incluso con la ayuda de algunas raíces POM). Los complementos son demasiado inconsistentes, con errores, y es realmente difícil encontrar una documentation clara que explique qué se debe configurar, y así sucesivamente.

Así que me pregunto si cambiaré de Maven a ANT + Ivy . Por lo que he visto hasta ahora, parece bastante genial (hay varios administradores de conflictos para las resoluciones de dependencies de conflictos e incluso puedes escribir tu propio administrador de conflictos), no es necesario tener una herramienta adicional instalada y configurada (como ANT se ejecuta de forma nativa en Eclipse, mientras que Maven necesita un complemento independiente; por cierto, he probado los 3 complementos de Mavens y he encontrado que los tres tienen errores).

Sin embargo Maven 3 está en path, lo intentaré pero no espero que sea fundamentalmente diferente de Maven 2.

Hudson parecería una mejor opción que Luntbuild, también, pero esta parte no cambiará por ahora.

Y Subversion probablemente replaceá a CVS en un futuro cercano (incluso si casi no tengo ningún problema con CVS).

Un montón de buenos consejos aquí. Tengo solo algunas adiciones:

Creo que, a diferencia del rest, un IDE es una herramienta personal, y cada desarrollador debe tener cierta libertad para seleccionar el que mejor funcione para él. (Por ejemplo, a muchos les encanta Eclipse, mientras que lo abandoné por NetBeans porque la integración de Maven era, eh, problemática en Eclipse).

Pensé que iba a odiar a Maven, pero ahora me llevo bastante bien. El principal problema que tengo en estos días es averiguar dónde están documentadas las convenciones .

Aconsejo introducir herramientas de a una por vez. Si tratas de mecanizar todos los aspectos del desarrollo de software en una tienda especializada de un solo golpe, es probable que haya una resistencia masiva. Haga su caso de negocio y obtenga un acuerdo sobre una buena herramienta común, o simplemente obtenga permiso para configurarlo para su uso pero de una manera comúnmente accesible y permita que la gente vea lo que hace por usted. Después de algunos de estos, las personas desarrollarán el hábito de preguntarse cómo el aspecto X podría automatizarse, por lo que las herramientas adicionales deberían ser más fáciles de introducir.

Lo mejor que puede hacer sin interrumpir a otras personas y su forma de trabajar es configurar Hudson para ver el repository de CVS para cada uno de sus proyectos. Solo hacer eso le dará un lugar central para ver cvs commit posts.

El siguiente paso es conseguir que estos proyectos se compilen con Hudson. Para Eclipse esto normalmente significa cambiar a la ant o, como lo hicimos, usar ant4eclipse para modelar el process de construcción del eclipse existente. No es fácil pero vale la pena. Recuerde enviar correos electrónicos cuando se rompa la compilation, esto es extremadamente importante. Ant4eclipse requiere sets de proyectos en equipo, presentándolos en su organización. Hará felices a sus colegas la próxima vez que necesiten configurar un espacio de trabajo nuevo.

Cuando tienes una situación en la que tus cosas se construyen correctamente cada vez que alguien realiza cambios, considera la posibilidad de hacer que el código creado automáticamente sea el código para que realmente llegue al cliente. Como fue construido en el server de compilation y no en una máquina de desarrollo, usted sabe que puede reproducir la compilation. Eso es invaluable en una situación de "oye arregla esta versión antigua".