hamcrest / PyHamcrest

Hamcrest matchers for Python
http://hamcrest.org/
Other
766 stars 111 forks source link

Add has_getter() and has_getters() object matchers, based on has_property() #245

Closed luziferius closed 5 months ago

luziferius commented 5 months ago

This PR adds two new matchers, has_getter(name, matcher) and has_getters(dict[str, matcher]) and overloads, similar to has_property() and has_properties().

In fact, I forked the property matchers to create the getter matchers.

Use case

There matchers are meant for objects that expose properties via callable getter methods. Prominent examples are the Qt GUI toolkit wrappers PyQt and PySide. The Qt objects expose properties via getter/setter pairs, and the Python wrappers translate them 1:1. Have a look at QRectF implementing a floating point rectangle, and QPointF. Object dimensions, coordinates and similar are accessible via getter methods.

The addition of has_getter() allows matching against those as if they were plain Python properties.

rect = QRectF(0, 1, 10, 11)  # x, y, width, height
assert_that(
    rect, has_getters({
        "topLeft":  has_getters({  # These return a QPointF
            "x": close_to(0),
            "y": close_to(1),}),
        "bottomRight":  has_getters({
            "x": close_to(10),
            "y": close_to(12),}),
        "width": close_to(10),
        "height": close_to(11),
        "isEmpty": False,
})
offbyone commented 5 months ago

While I appreciate the intent here, I don't think these are good fits for Hamcrest itself; we mostly avoid matchers that call code.

Please feel free to keep them as a local library; the code is well done.