Assertion
first you should make sure you understand its API and responsibility. It is responsible for determining whether or not some condition is true or false and to give details on the values that are used to determine whether that condition is true or false.AssertionResult
returned holds the information about whether the condition we were checking passed and the information about the values used. Since the assert()
method itself doesn't actually have any arguments everything that you might need for the check should be passed in to the constructor of the Assertion.Assertion
. Creating an AsyncAssertion
follows the same principles except that its assert()
method returns a Promise
that should resolve to the AssertionResult
.Assertion
MUST NOT throw an exception unless a truly unexpected circumstance has occurred. If an exception could be expected to be thrown during your condition checking you should catch it, mark your AssertionResult
as failed, and provide the appropriate information about that thrown exception.AssertionResult
MUST include summary information about both the normal case and the not case. An Assertion
SHOULD never make assumptions about whether it is being called in the normal case or the not case. If you haven't done so you can read up about the not case in "Getting Started".Widget
produced by a given WidgetService
has the correct name. Now, let's actually write our custom implementation!AssertionMessage
used to provide a summary of the assertion. The summary shouldn't go into heavy details about any potential problems with the assertion, just a brief description of how the assertion failed. These messages are ultimately used as a fragment in a greater message. For example, if the assertion failed you might expect to see output like the following...Failed comparing that 2 values are equal to one another.
Succeeded comparing that 2 values are equal to one another.
Skipped comparing that 2 values are equal to one another.
AssertionMessage
implementations. However, in our example none of the existing implementations really does what we need it to do. We will create our own, in this case an anonymous class that implements the AssertionMessage
interface.AssertionMessage
. Just like summary messages this implementation requires providing both the normal and not use cases.AssertionResult
. To create concrete implementations of this interface you can use the AssertionResultFactory
or roll your own! For our example we'll make use of the existing factory. Continuing to build upon what we've worked on so far let's finish off our custom Assertion
!assert()->widgetServiceCreatesNamedWidget('widgetName', $widgetService)
in your test cases to actually invoke your Assertion. We'll accomplish this by implementing the CustomAssertionPlugin
provided by the framework.