Hone logo
Hone
Problems

Implementing toHaveLength in Jest

Jest's built-in matchers are powerful, but sometimes you need to extend them to handle specific data types or validation scenarios. This challenge asks you to implement a custom Jest matcher called toHaveLength that verifies if an array or string has a specific length. This is a common validation task, and creating custom matchers allows you to make your tests more readable and maintainable.

Problem Description

You need to create a Jest custom matcher named toHaveLength. This matcher should accept a single argument, representing the expected length. The matcher should then compare the length of the input value (which is expected to be either an array or a string) with the expected length. The matcher should return a result indicating whether the actual length matches the expected length.

Key Requirements:

  • Type Handling: The matcher must correctly handle both arrays and strings as input.
  • Length Calculation: The matcher must accurately determine the length of the input value using the appropriate method (.length for arrays and strings).
  • Clear Error Messages: When the assertion fails, the matcher should provide a clear and informative error message indicating the expected length and the actual length.
  • Pass/Fail Logic: The matcher should return true if the actual length matches the expected length and false otherwise.

Expected Behavior:

  • When the input value's length matches the expected length, the matcher should pass.
  • When the input value’s length does not match the expected length, the matcher should fail, displaying a message like: "Expected array/string to have length ${expectedLength}, but got ${actualLength}".

Edge Cases to Consider:

  • Null or Undefined Input: The matcher should handle cases where the input value is null or undefined gracefully, ideally by failing the assertion with a descriptive error message.
  • Non-Array/String Input: The matcher should handle cases where the input is neither an array nor a string. A failure with a descriptive error message is appropriate.
  • Negative Expected Length: While less common, consider how the matcher should behave if a negative expected length is provided. Failing the assertion is a reasonable approach.

Examples

Example 1:

Input: [1, 2, 3, 4] and 4
Output: true
Explanation: The array has a length of 4, which matches the expected length of 4.

Example 2:

Input: "hello" and 5
Output: true
Explanation: The string "hello" has a length of 5, which matches the expected length of 5.

Example 3:

Input: [1, 2, 3] and 5
Output: false
Explanation: The array has a length of 3, which does not match the expected length of 5. The error message should indicate this discrepancy.

Example 4: (Edge Case)

Input: null and 0
Output: false
Explanation: The input is null. The matcher should fail with an appropriate error message.

Constraints

  • The matcher must be implemented using TypeScript.
  • The matcher should be compatible with Jest's assertion API.
  • The matcher should provide clear and helpful error messages.
  • The matcher should handle both arrays and strings.
  • The matcher should not introduce any performance regressions.

Notes

  • You'll need to create a Jest custom matcher factory function.
  • Within the factory function, you'll define the matcher logic.
  • Use expect.extend to register your custom matcher with Jest.
  • Consider using template literals to construct the error messages for better readability.
  • Think about how to handle different input types and edge cases to make your matcher robust.
Loading editor...
typescript