Pregunta

¿Cómo comenzarías a mejorar un sistema realmente malo?

Permítanme explicar a qué me refiero antes de recomendar crear pruebas unitarias y refactorizar. Podría usar esas técnicas, pero eso no tendría sentido en este caso.

En realidad, el sistema está tan roto que no hace lo que debe hacer.

Por ejemplo, el sistema debe contar cuántos mensajes envía. Funciona principalmente, pero en algunos casos se "olvida". para aumentar el valor del contador de mensajes. El problema es que muchos otros módulos con sus propias soluciones se basan en este contador que si corrijo el contador, el sistema en su conjunto se volvería peor de lo que es actualmente. La solución podría ser modificar todos los módulos y eliminar sus propias correcciones, pero con más de 150 módulos que requerirían tanta coordinación que no me lo puedo permitir.

Aún peor, hay algunos problemas que tienen soluciones no en el sistema en sí, sino en la cabeza de las personas. Por ejemplo, el sistema no puede representar más de cuatro mensajes relacionados en un grupo de mensajes. Algunos servicios requerirían cinco mensajes agrupados. El departamento de contabilidad conoce esta limitación y cada vez que cuenta los mensajes para estos servicios, cuenta los grupos de mensajes y los multiplica por 5/4 para obtener el número correcto de mensajes. No hay absolutamente ninguna documentación sobre estas desviaciones y nadie sabe cuántas cosas están presentes en el sistema ahora.

Entonces, ¿cómo comenzarías a trabajar para mejorar este sistema? ¿Qué estrategia seguirías?

Algunas cosas adicionales: soy un ejército de un solo hombre trabajando en esto, por lo que no es una respuesta aceptable contratar suficientes hombres y rediseñar / refactorizar el sistema. Y en unas pocas semanas o meses realmente debería mostrar una progresión visible, por lo que tampoco es una opción refactorizarme en un par de años.

Algunos detalles técnicos: el sistema está escrito en Java y PHP, pero no creo que eso realmente importe. Hay dos bases de datos detrás, una Oracle y una PostgreSQL. Además de las fallas mencionadas antes, el código en sí mismo también huele, está realmente mal escrito y documentado.

Información adicional:

El problema del contador no es un problema de sincronización. Las declaraciones counter ++ se agregan a algunos módulos y no se agregan a otros módulos. Una solución rápida y sucia es agregarlos donde faltan. La solución larga es hacer que sea un aspecto para los módulos que lo necesitan, haciendo imposible olvidarlo más tarde. No tengo problemas para arreglar cosas como esta, pero si hiciera este cambio, rompería con otros 10 módulos.

Actualización:

Acepté la respuesta de Greg D. Incluso si me gusta más Adam Adam, no me ayudaría saber qué sería lo ideal. Gracias a todos por las respuestas.

¿Fue útil?

Solución

  1. Apaga los fuegos . Si hay algún problema de prioridad crítica, cualesquiera que sean, primero debe resolverlos. Hackéalo si es necesario, con una base de código maloliente, está bien. Sabes que lo mejorarás en el futuro. Esta es su técnica de ventas dirigida a quien sea que esté informando.
  2. Elija algunas frutas bajas. Supongo que es relativamente nuevo en este software en particular y que se le encargó nuevamente que se encargara de ello. Encuentre algunos problemas aparentemente fáciles en un subsistema relacionado del código que no debería tomar más de un día o dos para resolver cada uno, y corríjalos. Esto puede implicar refactorización, o puede que no. El objetivo es familiarizarse con el sistema y con el estilo del autor original. Es posible que no tenga mucha suerte (uno de los dos incompetentes que trabajaban en mi sistema antes que yo siempre reparaba sus comentarios con cuatro signos de puntuación en lugar de uno, lo que hacía que fuera muy fácil distinguir quién escribió el segmento de código en particular). pero desarrollará una idea de las debilidades del autor para que sepa qué buscar. Acoplamiento extenso y estrecho con el estado global versus poca comprensión de las herramientas de lenguaje, por ejemplo.
  3. Establezca un gran objetivo. Si su experiencia es paralela a la mía, se encontrará cada vez más en un código de espagueti en particular a medida que realiza el paso anterior. Este es el primer nudo que necesitas desenredar. Con la experiencia que ha adquirido al comprender el componente y el conocimiento sobre lo que el autor original probablemente hizo mal (y, por lo tanto, lo que debe tener en cuenta), puede comenzar a imaginar un mejor modelo para este subconjunto del sistema. No se preocupe si todavía tiene que mantener algunas interfaces desordenadas para mantener la funcionalidad, solo dé un paso a la vez.

Espuma, enjuague, repita! :)

Con el tiempo, considere agregar pruebas unitarias para su nuevo modelo un nivel debajo de sus interfaces con el resto del sistema. No grabe las malas interfaces en el código a través de pruebas que las usan, las cambiará en una iteración futura.

Abordar los problemas particulares que menciona:

Cuando se encuentre con una situación en la que los usuarios estén trabajando manualmente, hable con los usuarios sobre cómo cambiarla. Verifique que aceptarán el cambio si lo proporciona antes de dedicarle tiempo. Si no quieren el cambio, su trabajo es mantener el comportamiento roto.

Cuando te encuentras con un componente defectuoso con el que han funcionado muchos otros componentes, adopto una técnica de componente paralelo. Cree un contador que funcione como debería funcionar el existente . Proporcione una interfaz similar (o, si es práctica, idéntica) y deslice el nuevo componente en la base de código. Cuando toque componentes externos que funcionan alrededor del que está roto, intente reemplazar el componente antiguo por el nuevo. Interfaces similares facilitan la portabilidad del código, y el componente antiguo sigue existiendo si falla el nuevo. No elimine el componente anterior hasta que pueda.

Otros consejos

¿Qué se te pide ahora? ¿Se le pide que implemente la funcionalidad o corrija errores? ¿Saben siquiera lo que quieren que hagas?

Si no tiene la mano de obra, el tiempo o los recursos para " arreglar " todo el sistema, entonces todo lo que puede hacer es rescatar agua. Estás diciendo que deberías poder hacer un "progreso visible" dentro de unos meses Bueno, dado que el sistema es tan malo como lo describió, en realidad puede empeorarlo. Bajo presión para hacer algo notable, simplemente agregará código y hará que el sistema sea aún más complicado.

Necesitas refactorizar, eventualmente. No hay manera de evitarlo. Si puede encontrar una forma de refactorizar que sea visible para sus usuarios finales, sería ideal , incluso si lleva de 6 a 9 meses o un año en lugar de "unos pocos meses". Pero si no puede, entonces tiene que elegir:

  • Refactor, y corre el riesgo de ser visto como "no lograr nada" a pesar de tus esfuerzos
  • No refactorice, logre "visible" objetivos y hacer que el sistema sea más complicado y más difícil de refactorizar algún día. (Tal vez después de encontrar un trabajo mejor, y espero que el próximo desarrollador que venga nunca sepa dónde vives).

Cuál es el más beneficioso para usted personalmente depende de la cultura de su empresa. ¿Decidirán algún día contratar más desarrolladores o reemplazar este sistema completamente con algún otro producto?

Por el contrario, si sus esfuerzos para " arreglar cosas " en realidad rompen otras cosas, ¿comprenderán la monstruosidad que se le pide que aborde sin ayuda?

No hay respuestas fáciles aquí, lo siento. Debe evaluar en función de su situación única e individual.

Este es un libro completo que básicamente dirá prueba unitaria y refactorización, pero con consejos más prácticos sobre cómo hacerlo

http://ecx.images-amazon.com/images/I/51RCXGPXQ8L._SL500_AA240_.jpg

http://www.amazon.com/Working-Effectively-Legacy-Robert -Martin / dp / 0131177052

Abre el directorio que contiene este sistema con el Explorador de Windows. Luego, presione Ctrl-A, y luego Shift-Delete. Eso suena como una mejora en su caso.

En serio: sin embargo, ese contador parece tener problemas de seguridad de subprocesos. Pondría un candado alrededor de las funciones crecientes.

Y con respecto al resto del sistema, no puedes hacer lo imposible, así que intenta hacer lo posible. Necesita atacar su sistema desde dos frentes. Primero, cuide los problemas más visibles y problemáticos para que pueda mostrar el progreso. Al mismo tiempo, debe lidiar con los problemas de infraestructura más, para que tenga la oportunidad de solucionarlo algún día.

Buena suerte, y que la fuente esté contigo.

Elija un área que sería de dificultad media para refactorizar. Cree un esqueleto del código original con solo las firmas de método de los existentes; tal vez use una interfaz incluso. Entonces comienza a hackear. Incluso puede señalar el " nuevo " métodos a los antiguos hasta llegar a ellos.

Luego, prueba, prueba, prueba. Dado que no hay pruebas unitarias, ¿tal vez solo use buenas pruebas anticuadas de unidades activadas por voz (personas)? O escriba sus propias pruebas a medida que avanza.

Documente su progreso a medida que avanza en algún tipo de repositorio, incluidas las frustraciones y las preguntas, de modo que cuando el próximo pobre idiota que obtenga este proyecto no esté donde está :).

Una vez que termine la primera parte, pase a la siguiente. La clave es construir sobre el progreso incremental, por eso no debes comenzar con la parte más difícil primero; será demasiado fácil desmoralizarse.

Joel tiene un par de artículos sobre reescritura / refactorización:

http://www.joelonsoftware.com/articles/fog0000000069.html

http://www.joelonsoftware.com/articles/fog0000000348.html

He estado trabajando con un sistema heredado con las mismas características durante casi tres años y no conozco ningún atajo.

Lo que más me molesta con nuestro sistema heredado es que no se me permite corregir algunos errores, ya que muchas otras funciones podrían romperse si los soluciono. Esto requiere soluciones feas o crear nuevas versiones de funciones antiguas. Las llamadas a las funciones antiguas se pueden reemplazar por una nueva a la vez (durante la prueba).

No estoy seguro de cuál es el objetivo de su tarea, pero le recomiendo encarecidamente que toque la menor cantidad de código posible. Solo haz lo que necesites hacer.

Es posible que desee obtener la mayor cantidad de documentación posible entrevistando a personas. Esta es una tarea enorme, ya que no sabes qué preguntas hacer, y la gente habrá olvidado muchos detalles.

Aparte de eso: asegúrate de que te paguen y tengas suficiente apoyo moral. Habrá llanto y crujir de dientes ...

Bueno, debes comenzar en alguna parte, y parece que hay errores que necesitan ser reparados. Trabajaría a través de esos errores, haciendo refactorizaciones rápidas y escribiendo cualquier prueba de unidad posible en el camino. También usaría una herramienta como SourceMonitor para identificar algunas de las partes de código más 'complejas' en el sistema y ver si puedo simplificar su diseño de alguna manera. En última instancia, solo tiene que aceptar que será un proceso lento y dar pequeños pasos hacia un sistema mejor.

Intentaría elegir una parte del sistema que pudiera extraerse y reescribirse aisladamente con bastante rapidez. Incluso si no hace mucho, podría mostrar un progreso bastante rápido y no tiene el problema de interactuar directamente con el código heredado.

Con suerte, si pudiera elegir algunas de esas tareas, lo verán haciendo progresos visibles, y podría presentar un argumento para contratar a más personas para reescribir los módulos más grandes. Cuando partes del sistema se basan en un comportamiento interrumpido, no tiene más opción que separarse antes de arreglar cualquier cosa.

Con suerte, podría construir gradualmente un equipo capaz de reescribir todo el lote.

Todo esto tendría que ir de la mano con un entrenamiento decente, de lo contrario, los viejos hábitos de las personas se mantendrán, y su trabajo tendrá la culpa cuando las cosas no funcionen como se esperaba.

¡Buena suerte!

Desprecia todo lo que existe actualmente que tiene problemas y escribe otros nuevos que funcionen correctamente. Documente tanto como pueda sobre lo que cambiará y coloque grandes letreros rojos intermitentes en todo el lugar que señalen esta documentación.

Al hacerlo de esa manera, puede mantener sus errores existentes (los que se están compensando en otro lugar) alrededor sin ralentizar su progreso hacia la obtención de un sistema de trabajo real.

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