skip to content

Walk through the common Hamcrest core matchers (is, equalTo, not, nullValue, containsString, hasItem) — what does each check and how do you read them?

level: juniorimportance: should knowfreq 60%

answer

  1. is(...) = sugar, equalTo = real check
  2. is(5) auto-wraps to is(equalTo(5))
  3. not(...) inverts any matcher
  4. hasItem = at least one matches; contains = exact ordered
  5. Matchers nest: hasItem(greaterThan(10))

basics

~10 s

equalTo checks equality, is wraps a matcher to read nicer, not inverts, nullValue checks for null, containsString checks a substring, and hasItem checks a collection contains an element. You combine them like assertThat(list, hasItem(equalTo(3))).

solid answer

~40 s

The everyday Hamcrest vocabulary: equalTo(x) passes when the value .equals(x). is(...) is pure syntactic sugar — is(equalTo(5)) and is(5) (it auto-wraps a plain value in equalTo) mean the same, just more readable. not(matcher) inverts any matcher, e.g. not(equalTo(0)). nullValue()/notNullValue() check null-ness. For strings, containsString("err"), startsWith, endsWith, and equalToIgnoringCase. For collections, hasItem(matcher) passes if at least one element matches, hasItems(...) for several, and hasSize(n). Because matchers nest, you compose them: hasItem(greaterThan(10)) means 'has at least one element greater than 10'. The power is that every slot that takes a value can instead take a matcher, so the vocabulary multiplies combinatorially rather than needing a dedicated assert per case.

go deeper

for a junior

Knows equalTo, is, not, nullValue, containsString, hasItem and can read them aloud.

for a middle

Distinguishes hasItem vs contains vs containsInAnyOrder vs everyItem and nests matchers correctly.

for a senior

Chooses the most precise matcher for clear failure messages and avoids over/under-specifying collection assertions.

for a principal

Guides the team on a consistent matcher vocabulary and reviews assertions for precision and readability.

## The idea: a small vocabulary that nests Hamcrest ships a set of *factory methods* (static methods that build matcher objects). Learning Hamcrest is mostly learning this vocabulary and the fact that matchers **nest** — anywhere a matcher expects a value, you can hand it another matcher instead. That nesting is what makes a tiny set of words very expressive. ## The core matchers **`equalTo(x)`** — the workhorse. Passes when `actual.equals(x)`. For arrays it does element-wise comparison. **`is(...)`** — *decoration only*, it changes nothing about the check, just readability. Two forms: - `is(matcher)` wraps another matcher: `is(equalTo(5))` reads 'is equal to 5'. - `is(value)` is a shortcut that auto-wraps the value in `equalTo`, so `is(5)` == `is(equalTo(5))` == `equalTo(5)`. **`not(...)`** — inverts. `not(equalTo(0))` passes when the value is not 0; `not(0)` also works (auto-wrap). It flips both the pass/fail and the description. **`nullValue()` / `notNullValue()`** — check for `null` / non-`null`. (`is(nullValue())` reads nicely.) **String matchers** — `containsString("sub")` (substring present), `startsWith("...")`, `endsWith("...")`, `equalToIgnoringCase("...")`, `equalToCompressingWhiteSpace("...")`, and `matchesPattern(regex)`. **Collection / iterable matchers** — - `hasItem(x)` / `hasItem(matcher)`: the collection contains **at least one** element equal to / matching the argument. - `hasItems(a, b)`: contains each of these (in any order). - `hasSize(n)`: exactly n elements. - `everyItem(matcher)`: **all** elements match. - `contains(a, b, c)`: exactly these elements, **in order**. - `containsInAnyOrder(a, b, c)`: exactly these, any order. - `emptyCollectionOf(...)` / `empty()`. ## Composition examples Because of nesting: ``` assertThat(names, hasItem(equalTo("Bob"))); // contains "Bob" assertThat(names, hasItem(startsWith("Bo"))); // some name starts with "Bo" assertThat(scores, everyItem(greaterThan(0))); // all positive assertThat(value, is(not(nullValue()))); // not null ``` ## Reading them aloud The vocabulary is deliberately English-like: `assertThat(temperature, is(greaterThan(20)))` reads 'assert that temperature is greater than 20'. The `is`/`a`/`an` words are sugar that exist only to make that reading smooth. ## Terms - *Factory method*: a static method that returns a built object (here, a matcher). - *Substring*: a contiguous run of characters inside a larger string. - *Iterable/collection matcher*: a matcher that inspects the elements of a list/set/array. - *.equals*: Java's equality method; `equalTo` delegates to it. ## Gotcha `hasItem(x)` means 'at least one element equals x', NOT 'the list equals [x]'. To assert the whole list, use `contains(...)` (ordered, exact) or `containsInAnyOrder(...)`.

  • What is the difference between contains(...) and containsInAnyOrder(...)?
    Both assert the collection holds exactly those elements and no others; contains requires that exact order, containsInAnyOrder ignores order.
  • How do you assert a list has at least one element greater than 10?
    assertThat(list, hasItem(greaterThan(10))) — hasItem takes a nested matcher, passing if any element satisfies it.

saying these in an interview costs you the question

  • Thinking is(...) performs the comparison itself (it's only sugar)
  • Believing hasItem(x) asserts the whole list equals [x]
  • Using equalTo to compare object identity (it uses .equals, not ==)
  • Confusing contains (exact, ordered) with hasItems (subset, any order)

context