Hamcrest allows you to create pretty complicated and flexible assertions. Just remember:
"You can" does not mean "you should".
The following example shows how we can ensure that there is an HTML form and password entered in it is not weak:
$html = '<div>
<form>
<input name="password" value="strong password"/>
</form>
</div>';
assertThat($html, is(htmlPiece(
havingChild(
both(withTagName('form'))
->andAlso(
havingDirectChild(
allOf(
withTagName('input'),
withAttribute('name')->havingValue('password'),
withAttribute('value')->havingValue(not('weak password')))))))));
Usage limitations:
- Each HTML assertion starts with
htmlPiece()
call (is()
can be used to improve readability) - One of
havingRootElement()
,havingDirectChild()
orhavingChild()
needed to be passed as an argument tohtmlPiece()
Information about general Hamcrest usage can be found at Hamcrest GitHub repository.
-
htmlPiece()
- checks that string is a valid HTML, parses it and passes control to given matcher if one presentassertThat('<p></p>', is(htmlPiece())); // Just checking that string is a valid piece of HTML
-
havingRootElement
- checks given constraint against root element of HTML. NOTE: Can be passed only tohtmlPiece()
assertThat('<p></p>', htmlPiece(havingRootElement(withTagName('p'))));
-
havingDirectChild
- checks given constraint against direct childrenassertThat('<p><b></b></p>', htmlPiece(havingRootElement(havingDirectChild(withTagName('b')))));
-
havingChild
- checks given constraint against all childrenassertThat('<p><b></b></p>', htmlPiece(havingChild(withTagName('b'))));
-
withTagName
- checks given constraint against tag nameassertThat('<p><b></b></p>', htmlPiece(havingChild(withTagName( either(equalTo('i'))->orElse(equalTo('b')) ))));
-
withAttribute
- checks given constraint against elements attributes comparing names and valuesassertThat('<p><input required></p>', htmlPiece(havingChild(withAttribute('required'))));
assertThat('<p><input data-value="some data"></p>', htmlPiece(havingChild( withAttribute(startsWith('data-'))->havingValue('some data'))));
-
withClass
- checks given constraint against element's class listassertThat('<p class="class1 class2 class3"></p>', htmlPiece(havingChild( withClass('class2'))));
-
havingTextContents
- checks given constraint against elements text contentsassertThat('<div><p>this is Some Text</p></div>', htmlPiece(havingChild( havingTextContents(containsString('some text')->ignoringCase()))));
-
tagMatchingOutline
- tolerantly checks that tag matches given outline (outline - tag representation in HTML format)\That means:
- Element's tag name is equal to outline's tag name
- Element has all the attributes that outline has with the same values. If element has more attributes than outline it still matches.
- NOTE: Attribute
class
is treated in a different manner (see further). - NOTE: If attribute outlined is boolean, then its value in element won't be checked, just presence.
- NOTE: Attribute
- Element has all html classes that outline has.
This will pass:
assertThat('<form><input id="id-pass" name="password" class="pretty green" required="required"></form>', htmlPiece(havingChild( tagMatchingOutline('<input name="password" class="green" required>') )));