Hone logo
Hone
Problems

Angular Component Testing: User Profile Display

This challenge focuses on writing effective component tests for an Angular component responsible for displaying user profile information. Understanding how to isolate and test components is a fundamental skill for building robust and maintainable Angular applications.

Problem Description

You are tasked with creating unit tests for an Angular component named UserProfileComponent. This component receives a User object as an input property and displays the user's name, email, and a profile image.

Your goal is to write comprehensive tests that verify the component's behavior under different scenarios, including valid data, missing data, and changes to the input properties.

Key Requirements:

  • Test that the component correctly displays the user's name.
  • Test that the component correctly displays the user's email.
  • Test that the component displays a placeholder image if no imageUrl is provided in the User object.
  • Test that the component displays the provided imageUrl when it exists.
  • Test that the component updates its display correctly when the @Input() user property changes.

Expected Behavior:

  • When a User object with all properties is provided, the component should render the name, email, and the specified image URL.
  • When a User object is provided without an imageUrl, a default placeholder image should be displayed.
  • When the user input property is updated (e.g., by a parent component), the displayed information should reflect the new user data.

Edge Cases to Consider:

  • What happens if the user input is null or undefined initially? (Though for this challenge, assume a valid User object or null/undefined will be provided).
  • How do you simulate changes to the @Input() property in your tests?

Examples

Let's define a simple User interface for clarity:

export interface User {
  id: number;
  name: string;
  email: string;
  imageUrl?: string; // Optional image URL
}

Example 1: Displaying a Full User Profile

  • Input:

    const mockUser: User = {
      id: 1,
      name: 'Alice Smith',
      email: 'alice.smith@example.com',
      imageUrl: 'https://example.com/alice.jpg'
    };
    
  • Expected Output (within the component's rendered DOM):

    • An element (e.g., <h1> or <p>) containing the text "Alice Smith".
    • An element (e.g., <p>) containing the text "alice.smith@example.com".
    • An <img> tag with its src attribute set to "https://example.com/alice.jpg".
  • Explanation: The component correctly renders all provided user details, including the specific image URL.

Example 2: Displaying a User with a Placeholder Image

  • Input:

    const mockUser: User = {
      id: 2,
      name: 'Bob Johnson',
      email: 'bob.j@example.com',
      // imageUrl is missing
    };
    
  • Expected Output (within the component's rendered DOM):

    • An element containing the text "Bob Johnson".
    • An element containing the text "bob.j@example.com".
    • An <img> tag with its src attribute set to a predefined placeholder URL (e.g., 'assets/images/placeholder.png' - assume this is configured in your test setup or component).
  • Explanation: Since imageUrl is not provided, the component falls back to displaying a default placeholder image.

Example 3: Updating User Information

  • Initial Input:

    const initialUser: User = {
      id: 3,
      name: 'Charlie Brown',
      email: 'charlie.b@example.com',
    };
    
  • Updated Input:

    const updatedUser: User = {
      id: 3,
      name: 'Charles Brown', // Name changed
      email: 'charles.brown@example.com', // Email changed
      imageUrl: 'https://example.com/charles.png' // Image added
    };
    
  • Expected Behavior:

    1. Initially, the component displays "Charlie Brown", "charlie.b@example.com", and a placeholder image.
    2. After the user input property is updated to updatedUser, the component's DOM should update to display "Charles Brown", "charles.brown@example.com", and the image from 'https://example.com/charles.png'.
  • Explanation: The component reacts to changes in its @Input() property and re-renders the UI accordingly.

Constraints

  • Use the Angular Testing Utilities (e.g., TestBed, ComponentFixture).
  • Your tests should be written in TypeScript.
  • Assume the UserProfileComponent has an @Input() property named user of type User.
  • Assume the component's template uses selectors like [data-testid="user-name"], [data-testid="user-email"], and [data-testid="user-image"] for easy querying.
  • The placeholder image URL will be 'assets/images/placeholder.png'.

Notes

  • Consider using fixture.detectChanges() after setting input properties to ensure Angular updates the component's view.
  • To test changes to @Input() properties, you can directly set the componentInstance.user property and then call fixture.detectChanges().
  • Focus on testing the component in isolation. Do not worry about the data fetching or any parent component logic.
  • The User interface should be defined or imported in your test file.
  • You'll likely need to mock any dependencies the UserProfileComponent might have (though for this basic component, it's unlikely to have complex dependencies).
  • Think about how to select elements in the DOM within your tests using the provided data-testid attributes.
Loading editor...
typescript