mensahs / mockito

Automatically exported from code.google.com/p/mockito
0 stars 0 forks source link

ArgumentMatcher implementation providing method-signature with generic parameter #398

Open GoogleCodeExporter opened 8 years ago

GoogleCodeExporter commented 8 years ago
Hi,

what do you think about an abstract implementation for an ArgumentMatcher that 
provides its subclasses with a method with a generic parameter instead of the 
java.lang.Object that has to be dealt with in every implementation? 

Something like this:
http://pastebin.com/dASUjFBz

At least in my implementations of ArgumentMatchers, this spares me one 
unnecessary cast and an if-check in every matcher. 
Maybe I'm missing something, though.

Best regards,
Florian

Original issue reported on code.google.com by florian....@gmail.com on 19 Nov 2012 at 4:57

GoogleCodeExporter commented 8 years ago
Yeah, this seems to be a nice idea

Original comment by gabor.li...@gmail.com on 19 Nov 2012 at 5:29

GoogleCodeExporter commented 8 years ago
Just copied the pastebin content to have it right in the issue

import org.mockito.ArgumentMatcher;

/**
 * Abstract implementation of {@link ArgumentMatcher} to get rid of the {@link Object} in the method-signature.
 *
 * @author florian.patzl
 *
 */
public abstract class GenericArgumentMatcher<T> extends ArgumentMatcher<T> {

        @SuppressWarnings("unchecked")
        @Override
        public boolean matches(Object argument) {
                try {
                        return doesMatch((T) argument);
                } catch (ClassCastException e) {
                        return false;
                }
        }

        protected abstract boolean doesMatch(T argument);
}

Could be interesting.

Original comment by brice.du...@gmail.com on 27 Nov 2012 at 5:00

GoogleCodeExporter commented 8 years ago
I don't understand why ArgumentMatcher<T> doesn't do this already?  The class 
is generic so why does the matches() method take Object and not T?

Original comment by DanKing...@googlemail.com on 22 Oct 2013 at 10:37

GoogleCodeExporter commented 8 years ago
Java8 variant: https://gist.github.com/4ndrew/e40db01a893a3fa20943

@FunctionalInterface
public static interface GenericArgumentMatcher<T>{
    boolean matches(T argument);
}

public static class GenericMatchers {
    public static class GenericArgumentMatcherWrapper<T> extends ArgumentMatcher<T> {
        private final GenericArgumentMatcher<T> delegate;

        public GenericArgumentMatcherWrapper(GenericArgumentMatcher<T> delegate) {
            this.delegate = delegate;
        }

        @SuppressWarnings("unchecked")
        @Override
        public boolean matches(Object argument) {
            try {
                return delegate.matches((T) argument);
            } catch (ClassCastException e) {
                return false;
            }
        }
    }

    public static <T> T argThat(GenericArgumentMatcher<T> matcher) {
        return Matchers.argThat(new GenericArgumentMatcherWrapper<T>(matcher));
    }
}

public class SampleTest {
    public void testTest() {
        final MyClass m = mock(MyClass.class);
        when(m.getSomething(GenericMatchers.argThat(a -> a.isValid()))).thenReturn(true);
    }
}

Original comment by Andrew.P...@gmail.com on 7 Oct 2014 at 5:00