001/* 002 * Copyright © 2018. Sir Wellington. 003 * Licensed under the Apache License, Version 2.0 (the "License"); 004 * you may not use this file except in compliance with the License. 005 * 006 * You may obtain a copy of the License at 007 * http://www.apache.org/licenses/LICENSE-2.0 008 * 009 * Unless required by applicable law or agreed to in writing, software 010 * distributed under the License is distributed on an "AS IS" BASIS, 011 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 012 * See the License for the specific language governing permissions and 013 * limitations under the License. 014 */ 015 016package tech.sirwellington.alchemy.test.mockito; 017 018import org.mockito.invocation.InvocationOnMock; 019import org.mockito.stubbing.Answer; 020import tech.sirwellington.alchemy.annotations.access.NonInstantiable; 021 022import static tech.sirwellington.alchemy.test.Checks.Internal.checkThat; 023 024/** 025 * This class contains a variety of useful answers for use in combination with Mockito. 026 * 027 * @author SirWellington 028 */ 029@NonInstantiable 030public final class MoreAnswers 031{ 032 033 MoreAnswers() throws IllegalAccessException 034 { 035 throw new IllegalAccessException("cannot instantiate class"); 036 } 037 038 039 /** 040 * For example: 041 * <p> 042 * <pre> 043 * 044 * {@code 045 * when(object.call("firstArg", 3)).then(returnFirst()); 046 * } 047 * Will return the {@code "firstArg"} string when it is called. 048 * </pre> 049 * 050 * @param <T> 051 * @return 052 * @see #returnArgumentAtIndex(int) 053 */ 054 public static <T> Answer<T> returnFirst() 055 { 056 return returnArgumentAtIndex(0); 057 } 058 059 /** 060 * An answer that returns one of the parameters as the return value. 061 * <p> 062 * Example: 063 * <pre> 064 * when(someMock.call(anyString(), anyString()).then(returnArgumentAtIndex(1)); 065 * 066 * String result = someMock.call("arg1", "arg2"); 067 * assertThat(result, is("arg2")); 068 * </pre> 069 * 070 * @param <T> 071 * @param index zero-based index which determines which parameter to return as an answer. 072 * @return 073 * @see #returnFirst() 074 */ 075 public static <T> Answer<T> returnArgumentAtIndex(final int index) 076 { 077 checkThat(index >= 0, "Index is out of bounds."); 078 079 return new Answer<T>() 080 { 081 @Override 082 public T answer(InvocationOnMock invocation) throws Throwable 083 { 084 if (index >= invocation.getArguments().length) 085 { 086 throw new IllegalArgumentException("Received an index of " + index + " but only " + invocation.getArguments().length + " arguments"); 087 } 088 089 return (T) invocation.getArguments()[index]; 090 } 091 }; 092 } 093}