Chaos Tool Suite (ctools)

Un conjunto completo de APIs y herramientas que mejoran la experiencia del desarrollador en Drupal, proporcionando utilidades para plugins, formularios, AJAX, contextos y más.

ctools
469,499 sites
214
drupal.org

Install

Drupal 11 v4.1.0
composer require 'drupal/ctools:^4.1'
Drupal 10, 9 v4.0.5
composer require 'drupal/ctools:^4.0'

Overview

Chaos Tool Suite (ctools) es principalmente un conjunto de APIs y herramientas diseñadas para mejorar la experiencia del desarrollador en Drupal. Proporciona una potente colección de utilidades y funciones auxiliares que otros módulos pueden aprovechar para construir funcionalidades complejas.

CTools ofrece una API de Form Wizard para crear formularios de múltiples pasos, una API de Context para envolver objetos en wrappers unificados, servicios de resolución de typed data, gestión de variantes de visualización de bloques y soporte para diálogos modales AJAX. También proporciona plugins de condición mejorados con soporte de restricciones y utilidades de tempstore para almacenar datos en caché a través de múltiples solicitudes de página.

El módulo se utiliza comúnmente como dependencia de otros módulos importantes de Drupal como Panels, Page Manager y varias extensiones de Layout Builder. Los usuarios finales típicamente interactúan con ctools indirectamente a través de módulos que dependen de él, mientras que los desarrolladores usan sus APIs directamente para construir funcionalidades avanzadas.

Features

  • API de Form Wizard - Un sistema completo para crear formularios de múltiples pasos con seguimiento automático de pasos, navegación anterior/siguiente, soporte AJAX e integración con SharedTempStore para preservar valores entre solicitudes
  • API de Context - Herramientas para envolver objetos (entidades, typed data) en wrappers de contexto unificados y proporcionar una API para crear, manipular y aceptar estos contextos como entrada
  • Typed Data Resolver - Servicio para resolver relaciones de typed data y convertir rutas de propiedades a objetos de contexto, permitiendo la navegación a través de relaciones complejas de entidades
  • Block Display Variant - Clase base abstracta para variantes de visualización que contienen y gestionan bloques con conocimiento completo del contexto y gestión de regiones
  • Sistema de Plugins de Relationship - Un gestor de plugins completo para crear y administrar relaciones entre entidades y propiedades de typed data
  • Soporte de Diálogos Modales AJAX - Trait y clases de comandos para crear fácilmente diálogos modales y formularios wizard habilitados para AJAX
  • Plugins de Condition Mejorados - EntityBundle condition extendida con soporte de restricciones que puede aplicar y eliminar restricciones de bundle de los contextos
  • Utilidades de Tempstore - Servicios para almacenar en caché objetos editados a través de múltiples solicitudes de página, permitiendo flujos de trabajo de edición complejos con múltiples formularios
  • Entity View Block - Bloques generados dinámicamente para visualizar cualquier tipo de entidad en cualquier modo de vista disponible
  • Clases de Plugin Collection - BlockPluginCollection y VariantPluginCollection para gestionar colecciones de plugins de bloques y variantes

Use Cases

Crear Wizards de Configuración de Múltiples Pasos

Usa la clase FormWizardBase para crear formularios de configuración de múltiples pasos. Extiende la clase, implementa getOperations() para definir tus pasos (cada uno con un título y clase de formulario), y configura rutas usando los controllers del wizard. El wizard maneja automáticamente la navegación entre pasos, el almacenamiento en caché de valores en SharedTempStore, soporte de modales AJAX y proporciona botones personalizables de 'Anterior/Siguiente/Finalizar'. Esto es comúnmente usado por módulos como Page Manager y Panels para crear configuraciones de página complejas.

Mostrar Campos de Entidad como Bloques

Habilita el submódulo ctools_block para obtener acceso a bloques de campo para cada tipo de entidad. Estos bloques pueden colocarse en cualquier región de bloques y mostrarán un solo campo de una entidad usando el sistema de contexto. Configura el formateador y la visualización del label por instancia de bloque. Útil para crear layouts flexibles donde los campos individuales necesitan colocarse independientemente.

Mejorar la Configuración de Bloques de Views

Habilita el submódulo ctools_views para obtener opciones de configuración adicionales al colocar bloques de Views. En la configuración de visualización de bloques de la vista, habilita las opciones deseadas de 'Permitir configuraciones' (elementos por página, desplazamiento, tipo de paginador, ocultar/ordenar campos, configurar/deshabilitar filtros, configurar ordenaciones). Cuando se coloca el bloque, los administradores pueden sobrescribir estas configuraciones por instancia, permitiendo que una sola vista se reutilice con diferentes configuraciones en todo el sitio.

Construir Sistemas de Visualización Conscientes del Contexto

Usa los servicios TypedDataResolver y ContextMapper para construir sistemas que pueden navegar relaciones de entidades y proporcionar funcionalidad consciente del contexto. El resolver puede convertir rutas estilo token como 'node:uid:name' en objetos de contexto apropiados con valores. Esto permite construir contenido dinámico que se adapta basándose en el contexto de la página actual, similar a la funcionalidad de Panels y Page Manager.

Crear Formularios de Diálogo Modal

Usa AjaxFormTrait y OpenModalWizardCommand para crear formularios de diálogo modal con AJAX. El trait proporciona métodos auxiliares para generar atributos AJAX, mientras que el comando puede abrir formularios wizard en diálogos modales. Esto es útil para interfaces de edición en línea o diálogos de configuración que no requieren una recarga completa de página.

Implementar Plugins de Relationship Personalizados

Crea plugins de Relationship personalizados implementando RelationshipInterface y usando la anotación @Relationship. Las relaciones definen cómo navegar de un contexto a otro (por ejemplo, de un nodo a su autor). El RelationshipManager descubre plugins en el directorio Plugin/Relationship. Esto es esencial para construir sistemas que necesitan acceder a datos relacionados basándose en el contexto actual.

Aplicar Restricciones Dinámicas a Contextos

Usa ConstraintConditionInterface implementada por EntityBundle para agregar o eliminar dinámicamente restricciones de contextos. Cuando se evalúa una condición, puede modificar las restricciones del contexto (por ejemplo, limitando un contexto de nodo a tipos de contenido específicos). Esto permite construir sistemas flexibles de control de acceso y filtrado de contenido que se adaptan basándose en la configuración de condiciones.

Crear Entidades de Vista Previa/Temporales

Habilita el submódulo ctools_entity_mask y define un tipo de entidad con una clave 'mask' apuntando a otro tipo de entidad. La entidad mask heredará todos los campos y configuración de visualización del tipo enmascarado pero usa un manejador de almacenamiento que no persiste datos. Esto es ideal para construir sistemas de vista previa o formularios de configuración que necesitan renderizar entidades sin guardarlas.

Tips

  • Al extender FormWizardBase, sobrescribe getOperations() para definir los pasos de tu wizard. Cada paso debe tener una clave 'form' con el nombre de clase completamente calificado del formulario y opcionalmente una clave 'title' para la etiqueta del paso.
  • Usa el método getWizardForm() del servicio ctools.wizard.factory con el tercer parámetro establecido en TRUE para habilitar soporte de modales AJAX para tus wizards.
  • El servicio deprecado ctools.serializable.tempstore.factory debe reemplazarse con el servicio tempstore.shared del core de Drupal. La funcionalidad es idéntica.
  • Al usar ctools_views, configura las opciones de 'Permitir configuraciones' en la visualización de bloques de la vista antes de colocar el bloque. Solo las configuraciones habilitadas aparecerán en el formulario de configuración del bloque.
  • La condición EntityBundle en ctools agrega soporte de restricciones que la condición del core carece. Si necesitas aplicar restricciones de bundle a contextos programáticamente, usa el método applyConstraints().
  • Para bloques de entity view, ten en cuenta la protección contra recursión - si intentas mostrar una entidad dentro de su propia vista, el bloque devolverá vacío para prevenir bucles infinitos.
  • El método convertTokenToContext() del TypedDataResolver puede navegar rutas de propiedades profundas como 'node:uid:field_profile:entity' para acceder a relaciones anidadas.

Technical Details

Hooks 2
hook_ctools_relationship_info_alter

Permite a los módulos alterar las definiciones de plugins de relationship descubiertas por el RelationshipManager.

hook_condition_info_alter (used by ctools)

CTools usa este hook para reemplazar las clases de condición de entity bundle del core con sus versiones mejoradas que soportan restricciones.

Troubleshooting 5
El formulario wizard pierde valores entre pasos

Asegúrate de que tu clase wizard implemente correctamente getTempstoreId() y getMachineName(). Los valores se almacenan en SharedTempStore usando estos identificadores. También verifica que el método submitForm() de tu formulario no sobrescriba incorrectamente los valores en caché.

Los bloques de campos de entidad no aparecen en la biblioteca de bloques

Habilita el submódulo ctools_block. Ten en cuenta que estos bloques están intencionalmente ocultos de Layout Builder - aparecen en la interfaz estándar de colocación de bloques pero no en el navegador de bloques de Layout Builder.

Las opciones de configuración del bloque de Views no se muestran

Primero, asegúrate de que ctools_views esté habilitado. Luego edita la vista y ve a la configuración de visualización de bloques. Bajo 'Permitir configuraciones', habilita las opciones específicas que quieres configurar por bloque (elementos por página, desplazamiento, ocultar campos, etc.).

Las restricciones de condición no se aplican

Verifica que tu plugin de condición implemente ConstraintConditionInterface. Llama a applyConstraints() con tu array de contextos después de configurar la condición. Recuerda llamar a removeConstraints() cuando la condición se elimine o reconfigure.

Los diálogos modales del wizard no se abren

Asegúrate de que la biblioteca core/drupal.dialog.ajax esté adjunta. El OpenModalWizardCommand maneja esto automáticamente, pero si usas llamadas AJAX manuales, necesitas adjuntar la biblioteca. También verifica que tu enlace tenga los atributos AJAX correctos de AjaxFormTrait::getAjaxAttributes().

Security Notes 3
  • El SerializableTempstoreFactory está deprecado. Migra al SharedTempStoreFactory del core que ha sido auditado para seguridad.
  • Al implementar wizards personalizados, asegúrate de que las verificaciones de acceso apropiadas estén en su lugar para cada paso. El servicio TempstoreAccess puede ayudar a validar el acceso a rutas basadas en tempstore.
  • Ten cuidado con el TypedDataResolver al exponer la navegación de relaciones a usuarios finales - podría potencialmente revelar información de estructura de datos si no se restringe apropiadamente.