Las pruebas unitarias son una parte esencial del desarrollo de software, ya que permiten verificar que las unidades individuales de código (como funciones, métodos o clases) funcionan correctamente. En Angular, las pruebas unitarias se realizan utilizando herramientas como Jasmine y Karma.

Objetivos de esta sección

  • Comprender la importancia de las pruebas unitarias.
  • Configurar el entorno de pruebas en Angular.
  • Escribir y ejecutar pruebas unitarias básicas.
  • Utilizar TestBed para configurar y probar componentes y servicios.

¿Qué son las Pruebas Unitarias?

Las pruebas unitarias son pruebas automatizadas que verifican el comportamiento de una pequeña parte del código, generalmente una función o un método. Estas pruebas ayudan a:

  • Detectar errores en etapas tempranas del desarrollo.
  • Facilitar el mantenimiento del código.
  • Asegurar que los cambios en el código no introduzcan nuevos errores.

Configuración del Entorno de Pruebas

Angular CLI viene preconfigurado con Jasmine y Karma para realizar pruebas unitarias. Jasmine es un framework de pruebas para JavaScript, mientras que Karma es un ejecutor de pruebas que permite ejecutar las pruebas en diferentes navegadores.

Instalación de Dependencias

Si has creado tu proyecto Angular con Angular CLI, las dependencias necesarias para las pruebas unitarias ya están instaladas. Si no, puedes instalarlas con los siguientes comandos:

npm install --save-dev jasmine-core karma karma-chrome-launcher karma-jasmine karma-jasmine-html-reporter

Estructura de Archivos de Pruebas

Por convención, los archivos de pruebas en Angular tienen la extensión .spec.ts. Estos archivos se colocan junto a los archivos de código que están probando. Por ejemplo, si tienes un componente app.component.ts, su archivo de prueba sería app.component.spec.ts.

Escribiendo una Prueba Unitaria Básica

Vamos a escribir una prueba unitaria básica para una función simple. Supongamos que tenemos una función sum en un archivo math.ts:

// math.ts
export function sum(a: number, b: number): number {
  return a + b;
}

El archivo de prueba para esta función sería math.spec.ts:

// math.spec.ts
import { sum } from './math';

describe('sum', () => {
  it('should return the sum of two numbers', () => {
    expect(sum(1, 2)).toBe(3);
  });

  it('should return a negative number if the sum is negative', () => {
    expect(sum(-1, -2)).toBe(-3);
  });
});

Explicación del Código

  • describe: Define un grupo de pruebas relacionadas.
  • it: Define una prueba individual.
  • expect: Realiza una afirmación sobre el resultado de la función.

Probando Componentes con TestBed

TestBed es una utilidad de Angular que permite configurar y probar componentes y servicios en un entorno de pruebas.

Ejemplo de Prueba de Componente

Supongamos que tenemos un componente app.component.ts:

// app.component.ts
import { Component } from '@angular/core';

@Component({
  selector: 'app-root',
  template: '<h1>{{title}}</h1>'
})
export class AppComponent {
  title = 'Hello Angular';
}

El archivo de prueba para este componente sería app.component.spec.ts:

// app.component.spec.ts
import { TestBed, ComponentFixture } from '@angular/core/testing';
import { AppComponent } from './app.component';

describe('AppComponent', () => {
  let component: AppComponent;
  let fixture: ComponentFixture<AppComponent>;

  beforeEach(() => {
    TestBed.configureTestingModule({
      declarations: [AppComponent]
    }).compileComponents();

    fixture = TestBed.createComponent(AppComponent);
    component = fixture.componentInstance;
  });

  it('should create the component', () => {
    expect(component).toBeTruthy();
  });

  it(`should have as title 'Hello Angular'`, () => {
    expect(component.title).toEqual('Hello Angular');
  });

  it('should render title in a h1 tag', () => {
    fixture.detectChanges();
    const compiled = fixture.nativeElement;
    expect(compiled.querySelector('h1').textContent).toContain('Hello Angular');
  });
});

Explicación del Código

  • TestBed.configureTestingModule: Configura un módulo de pruebas con los componentes necesarios.
  • TestBed.createComponent: Crea una instancia del componente para pruebas.
  • fixture.detectChanges(): Detecta cambios y actualiza la vista del componente.

Ejercicio Práctico

Ejercicio

Crea un componente greeting.component.ts que tenga una propiedad greeting y un método getGreeting(). Escribe pruebas unitarias para verificar que la propiedad y el método funcionan correctamente.

// greeting.component.ts
import { Component } from '@angular/core';

@Component({
  selector: 'app-greeting',
  template: '<p>{{greeting}}</p>'
})
export class GreetingComponent {
  greeting: string = 'Hello, World!';

  getGreeting(): string {
    return this.greeting;
  }
}

Solución

// greeting.component.spec.ts
import { TestBed, ComponentFixture } from '@angular/core/testing';
import { GreetingComponent } from './greeting.component';

describe('GreetingComponent', () => {
  let component: GreetingComponent;
  let fixture: ComponentFixture<GreetingComponent>;

  beforeEach(() => {
    TestBed.configureTestingModule({
      declarations: [GreetingComponent]
    }).compileComponents();

    fixture = TestBed.createComponent(GreetingComponent);
    component = fixture.componentInstance;
  });

  it('should create the component', () => {
    expect(component).toBeTruthy();
  });

  it(`should have as greeting 'Hello, World!'`, () => {
    expect(component.greeting).toEqual('Hello, World!');
  });

  it('should return the greeting', () => {
    expect(component.getGreeting()).toEqual('Hello, World!');
  });

  it('should render greeting in a p tag', () => {
    fixture.detectChanges();
    const compiled = fixture.nativeElement;
    expect(compiled.querySelector('p').textContent).toContain('Hello, World!');
  });
});

Conclusión

En esta sección, hemos aprendido la importancia de las pruebas unitarias y cómo configurarlas en un proyecto Angular. Hemos escrito pruebas unitarias básicas para funciones y componentes utilizando Jasmine y TestBed. Las pruebas unitarias son una herramienta poderosa para asegurar la calidad y la estabilidad del código, y su uso es una práctica recomendada en el desarrollo de aplicaciones Angular.

En la siguiente sección, exploraremos cómo realizar pruebas de componentes en mayor detalle, incluyendo la interacción con servicios y la simulación de dependencias.

Curso de Angular 2+

Módulo 1: Introducción a Angular

Módulo 2: Conceptos Básicos de TypeScript

Módulo 3: Componentes y Plantillas

Módulo 4: Directivas y Pipes

Módulo 5: Servicios e Inyección de Dependencias

Módulo 6: Enrutamiento y Navegación

Módulo 7: Formularios en Angular

Módulo 8: Cliente HTTP y Observables

Módulo 9: Gestión de Estado

Módulo 10: Pruebas en Angular

Módulo 11: Temas Avanzados

Módulo 12: Despliegue y Mejores Prácticas

© Copyright 2024. Todos los derechos reservados