Tengo un componente que estoy tratando de probar:
export const Block = ({ title }) => { const [isSmall, setIsSmall] = useState(false); reutrn ( <BlockContainer onBlockContainerResize={(width: number) => (width < 180 ? setIsSmall(true) : setIsSmall(false))} > <div className={isSmall ? 'title--small' : 'title'} data-testid={isSmall ? 'isSmall' : ''}> {title} </div> <div className={isSmall ? 'desc--small' : 'desc'}> {desc} </div> </BlockContainer> ) }Agregué un data-testid porque quiero evitar probar classNames, ya que esto va en contra de los principios de la biblioteca de pruebas de reacción. Solo quiero asegurarme de que si el contenedor está por debajo de 180 px, entonces isSmall se establece en verdadero.
Para mi prueba, estoy usando un div como contenedor en lugar del componente principal BlockContainer :
test('should set isSmall to true if container width is below 180px', () => { render( <div style={{ width: '170px' }}> <Block title="test title" desc="test description" /> </div> ); expect(within(screen.getByTestId('isSmall')).queryByText('test title')).toBeInTheDocument(); });Sin embargo, al intentar esto, isSmall no se establece en verdadero y, por lo tanto, no se establece la identificación de prueba de datos. Estoy confundido en cuanto a por qué sucede esto?
Aquí está la implementación de BlockContainer:
export const BlockContainer: FunctionComponent<BlockContainerProps> = ({ children, onBlockContainerResize, }) => { const blockRef = useRef<HTMLDivElement>(null); useResizeObserver(blockRef, (entry) => onBlockContainerResize?.(entry.contentRect.width)); return ( <div ref={blockRef} > {children} </div> ); };Al realizar pruebas con React Testing Library, es importante saber qué hacen otros componentes. Por ejemplo, está inicializando el estado isSmall en falso y solo lo está configurando en verdadero en la devolución de llamada de onBlockContainerResize , pero no está realizando ninguna acción para que esto suceda. Debe activar esa devolución de llamada para realizar el cambio.
Dijo que, en RTL, el objetivo principal es probar lo que ve el usuario final y burlarse de lo que hace el usuario final. Eso significa que para activar esa devolución de llamada, deberá imitar el comportamiento del usuario (por ejemplo, cambiar el tamaño del contenedor). Entonces, necesitamos saber cómo hace eso el usuario (dentro del componente BlockContainer ) y luego activarlo con un fireEvent de fuego de RTL, después de renderizar el componente y antes de afirmarlo.
Además, no pondría una propiedad data-testid en un div y la renderizaría según el estado. Eso acopla su prueba a la implementación del componente. Tomaría ese div y verificaría su tamaño, que es lo que haría el usuario final, ya que un usuario no conoce los estados internos.
Espero que estos consejos ayuden. De lo contrario, necesitaremos un ejemplo de la implementación de BlockContainer para ver cómo se puede desencadenar este evento.