Archyno
UMLDiagramas de estructura

Diagramas de componentes UML

El sistema como un conjunto de piezas reemplazables y los contratos entre ellas. Qué ofrece cada pieza, qué necesita y - la parte útil - qué tendrías que respetar para cambiar una.

13 min de lecturaUML 2.5.117 de 35

La respuesta corta

  • Un componente es una unidad reemplazable con un contrato definido - algo que podrías sacar a concurso - no simplemente una clase grande.
  • Cada componente lleva dos listas: lo que ofrece y lo que necesita. La mitad requerida es la que se omite, y es la que carga con las dependencias.
  • Una bola en un palo es una interfaz ofrecida, una media taza una requerida, y la bola encajada en la taza son ambas conectadas.
  • Un componente es lógico y un nodo es físico. En cuanto una caja adquiere un nombre de host o un número de instancias, estás dibujando un diagrama de despliegue.
Un diagrama de componentes UML. El componente Checkout depende de una interfaz IPayment, que realiza el componente Payment orchestrator. El orquestador depende a su vez de una interfaz ILedger, realizada por el componente Ledger.
Cuatro componentes y dos contratos. La flecha discontinua con triángulo hueco significa «esto lo implemento»; la flecha discontinua simple significa «esto lo necesito».

01Qué muestra#

Un diagrama de componentes describe un sistema como piezas reemplazables. Un componente en UML no es una clase cualquiera: es una unidad con frontera definida que, en principio, podría cambiarse por otra implementación de los mismos contratos sin que nada a su alrededor se entere.

Todo el valor está en esa definición. El diagrama te obliga a anotar, por cada pieza, exactamente dos cosas: qué proporciona y qué requiere. Esas dos listas son el contrato de la pieza con el resto del sistema, y son justo lo que necesitas al planificar una migración, dimensionar una reescritura o decidir si una frontera de servicio está en el sitio correcto.

02La notación#

ElementoNotaciónQué significa
Componenterectángulo con el icono de enchufeUna unidad reemplazable. El icono en la esquina es la forma de UML 2; la antigua ponía el icono en lugar de la caja.
Interfaz proporcionadaEl componente implementa este contrato. Se dibuja como realización hacia una «interface», o como bola en un palito.
Interfaz requeridaEl componente necesita que alguien la proporcione. Se dibuja como dependencia, o como zócalo: media copa en un palito.
Conector de ensamblajeuna bola encajada en un zócaloLa interfaz proporcionada de un componente conectada a la requerida de otro. La forma compacta de las dos filas anteriores.
Puertocuadrado pequeño en la fronteraUn punto de interacción con nombre. Úsalo cuando un componente tiene varios canales distintos: una API pública y otra de administración, por ejemplo.
Conector de delegaciónDe un puerto exterior a una parte interior: este contrato externo lo atiende en realidad esa pieza interna.

La forma de bola y zócalo (ball and socket) es la compacta y la que la mayoría de herramientas dibuja por defecto: una piruleta que sale de un componente es una interfaz que proporciona, media copa es una que requiere, y una bola descansando en un zócalo son las dos conectadas. Es la misma información que las flechas de arriba, en menos espacio. Usa la que a tus lectores les resulte más fácil; sé coherente dentro de un diagrama.

Cada marca que este tipo de diagrama puede llevar -ambas notaciones de interfaz, los conectores de ensamblaje y delegación, los puertos y los cuatro estereotipos que merecen escribirse- está recogida en los símbolos del diagrama de componentes.

03¿Cómo de grande es un componente?#

Es la pregunta en la que se atasca todo primer diagrama de componentes, y la especificación no ayuda: UML dice que un componente es una unidad reemplazable con un contrato definido y deja el tamaño enteramente en tus manos. Para una norma es la respuesta correcta y ante una pizarra es inútil, así que aquí está la regla de trabajo.

Un componente es aquello que podrías sacar a concurso. Si puedes imaginarte entregando a otro equipo las listas de interfaces proporcionadas y requeridas y diciendo «construid esto, no miraremos dentro», es un componente. Si esa entrega exigiera una conversación sobre las tripas, la frontera está dibujada en el sitio equivocado, y ese es el hallazgo, no un problema de dibujo que haya que sortear.

En la práctica suele caer en uno de estos niveles, y en cuál caiga te dice para qué sirve el diagrama.

  • Un servicio desplegable. Un repositorio, un pipeline, una guardia. La respuesta más común en cualquier cosa construida en la última década y el nivel al que merece la pena mantener el diagrama en el repositorio.
  • Una biblioteca o módulo. Dentro de un desplegable, cuando la discusión va de estructura interna: qué paquete puede depender de cuál. Aquí un diagrama de paquetes suele decir lo mismo más barato.
  • Un sistema entero. El mainframe, el CRM, el proveedor de pagos. El nivel del diagrama de contexto, donde lo que importa es de qué dependes y no cómo está construido.

Mezclar dos de esos niveles en un diagrama es el error que produce esos diagramas de componentes desbordados que la gente recuerda. Una imagen con tres microservicios, una biblioteca de utilidades y «SAP» son tres diagramas superpuestos, y ningún lector puede saber qué cajas son pares.

04Cómo leerlo bien#

La técnica de lectura más útil es tapar un componente con la mano. Lo que queda es su contrato: las interfaces que estaban conectadas a él. Si puedes entregar esa lista a otro equipo y decir «construid algo que satisfaga esto», el diagrama está haciendo su trabajo. Si no puedes -si reemplazar el componente exigiera conocer cosas que no están dibujadas- la frontera está en el sitio equivocado, y conviene saberlo antes de que alguien lo intente.

La segunda técnica es seguir las interfaces requeridas. Cada una es una dependencia que alguien tiene que satisfacer, y un ciclo en ese grafo es un problema arquitectónico real que un diagrama de componentes hace visible de inmediato.

Ambas técnicas se ven mejor aplicadas que descritas. Cinco diagramas de sistemas en los que probablemente hayas trabajado -un catálogo compartido, puertos y adaptadores, la sustitución de un sistema heredado, un anfitrión de plugins y un ciclo- se recorren en los ejemplos de diagramas de componentes, cada uno con la discusión que zanja.

05¿Qué caja estoy dibujando?#

Cinco tipos de diagrama son rectángulos unidos por líneas, y toda la diferencia está en qué es un rectángulo. Elegir el equivocado es el error más caro disponible aquí, porque el diagrama parecerá correcto y responderá a una pregunta que nadie hizo.

ElementoNotaciónQué significa
Componentesuna unidad reemplazableLas cajas son cosas que podrían cambiarse por otra implementación del mismo contrato. Las líneas son interfaces proporcionadas y requeridas. Responde: ¿qué promete cada pieza y qué necesita?
Clasesun tipoLas cajas son tipos del código. Las líneas son asociaciones, generalizaciones y dependencias. Responde: ¿cuál es la forma del código? Mira el diagrama de clases.
Paquetesun espacio de nombresLas cajas son agrupaciones: carpetas, espacios de nombres, módulos. Las líneas son dependencias permitidas. Responde: ¿qué puede importar qué?
Despliegueun nodoLas cajas son máquinas, contenedores y entornos de ejecución. Las líneas son rutas de comunicación. Responde: ¿dónde se ejecuta esto y sobre qué? Mira el diagrama de despliegue.
Estructura compuestauna parte dentro de un todoLas cajas son las partes de las que se compone un clasificador, dibujadas dentro de él. Responde: ¿de qué está hecha esta cosa por dentro?

El mismo rectángulo en cinco notaciones. Lee la columna del medio antes de dibujar: es la frase a la que todo el diagrama es una respuesta.

La duda que más aparece es componentes frente a despliegue, y la separación es limpia una vez dicha: un componente es una unidad lógica y un nodo una física. Un componente puede correr en cuarenta nodos; un nodo puede alojar una docena de componentes. En cuanto una caja de tu diagrama de componentes adquiere una región, un número de instancias o un nombre de host, ha dejado de ser un componente y el diagrama se ha convertido calladamente en dos.

Si conoces C4, su diagrama de contenedores cae casi exactamente donde un diagrama de componentes al nivel de servicio desplegable, y su propio nivel de «componentes» está un paso más adentro de lo que UML suele entender. Los vocabularios no encajan, así que escribe en el diagrama cuál usas: esa línea de leyenda evita la mayoría de las discusiones.

06Cuándo dibujar uno#

Úsalo cuando

  • Definir fronteras de servicio antes de dividir o fusionar sistemas
  • Documentar qué posee un equipo y de qué depende de otros
  • Planificar una sustitución: el contrato es exactamente lo que lo nuevo debe satisfacer
  • Revisar si las dependencias fluyen como la arquitectura afirma

Usa otra cosa cuando

  • Te refieres a máquinas y procesos físicos: usa un diagrama de despliegue
  • Te refieres al interior de un componente: usa un diagrama de estructura compuesta
  • Las partes son clases, no unidades reemplazables: usa un diagrama de clases
  • Hay tres servicios y todo el mundo sabe ya cómo se conectan

Los diagramas de componentes envejecen bien, lo cual es inusual. Las interfaces cambian mucho más despacio que el código que hay detrás, así que un diagrama de componentes versionado sigue siendo cierto mucho más tiempo que un diagrama de clases del mismo sistema, y en consecuencia merece más la pena mantenerlo.

07Errores comunes#

  1. Componentes que en realidad son clases. Si no puede reemplazarse de forma independiente de manera plausible, no es un componente. Usa un diagrama de clases.
  2. Dibujar solo las interfaces proporcionadas. Las requeridas llevan la información de dependencia, que es la mitad más útil.
  3. Flechas entre componentes sin interfaz. Una flecha desnuda dice «depende de algún modo», que es justo lo que este diagrama existe para precisar.
  4. Mezclar despliegue. Servidores, regiones y contenedores pertenecen a un diagrama de despliegue.
  5. Interfaces nombradas según el proveedor. ILedger está bien mientras haya un solo libro mayor; cuando puede haber dos implementaciones, nombra el contrato por la capacidad, no por el proveedor actual.

En una línea cada uno

  1. 01Un componente es una unidad reemplazable con un contrato definido, no solo una clase grande.
  2. 02Cada componente tiene dos listas: qué proporciona y qué requiere.
  3. 03La realización (triángulo hueco, discontinua) apunta a la interfaz implementada.
  4. 04La dependencia (flecha abierta, discontinua) apunta a la interfaz requerida.
  5. 05Bola y zócalo es la forma compacta de la misma información.
  6. 06Tapa un componente con la mano: lo que queda es lo que un sustituto debe satisfacer.

08Preguntas frecuentes#

¿Qué es la notación de bola y casquillo?

Es la forma abreviada de las interfaces. Una interfaz provista es una piruleta, un círculo pequeño sobre un palo. Una requerida es un casquillo, un semicírculo. Encajar la bola en el casquillo muestra que un componente satisface la dependencia de otro sin dibujar la interfaz como una clase.

¿Qué diferencia hay entre un diagrama de componentes y uno de clases?

Un diagrama de clases muestra tipos y su estructura interna. Uno de componentes muestra unidades desplegables y reemplazables y los contratos entre ellas, y oculta a propósito lo que hay dentro de cada una. Responde a qué tendrías que respetar para cambiar una pieza.

¿Qué es un puerto en UML?

Un cuadrado pequeño en el borde de un componente que representa un punto de interacción distinto. Los puertos permiten a un componente exponer varias interfaces separadas, por ejemplo una API de administración y otra pública, en lugar de una única superficie indiferenciada.

¿Cuándo merece la pena dibujar un diagrama de componentes?

Cuando el sistema tiene piezas que podrían reemplazarse o comprarse en vez de construirse, y la pregunta interesante es la interfaz entre ellas. Si nada del sistema es reemplazable, el diagrama solo repite la estructura de paquetes.

En esta serie

Lecturas relacionadas

Todos los artículos