Issue
I have a method in AccountService, how can I verify fields of account instance, for instance, I want to verify that created Account has USER role,
public ResponseEntity<CreateAccountResponse> createAccount(AccountCreateRequest accountCreateRequest) {
Account account = new Account();
account.setId(GenerateUtils.generateTokenWithPrefix(PrefixUUID.ACCOUNT));
account.setFirstName(accountCreateRequest.getFirstName());
account.setLastName(accountCreateRequest.getLastName());
account.setUserName(accountCreateRequest.getEmail());
//TODO assume that admin user should not create admin user
account.setRole(AccountRole.USER.toString());
account.setConfirmed(true);
account.setLocked(false);
account.setLoginAttempts(0);
account.setPassword(DigestUtils.sha256Hex(accountCreateRequest.getPassword()));
Account accountCreated = accountRepository.save(account);
CreateAccountResponse createAccountResponse = CreateAccountResponse.builder().id(accountCreated.getId()).confirmed(accountCreated.getConfirmed()).firstName(accountCreated.getFirstName()).lastName(accountCreated.getLastName()).locked(accountCreated.getLocked()).loginAttempts(accountCreated.getLoginAttempts()).role(accountCreated.getRole()).userName(accountCreated.getUserName()).build();
return ResponseEntity.status(HttpStatus.CREATED).body(createAccountResponse);
}
Solution
Since your AccountRepository
is mocked, you can catch the argument with ArgumentCaptor
with which the repository's save
method is called.
Smth like this:
@ExtendWith(MockitoExtension.class)
public class SimpleTest {
@InjectMocks
private AccountService accountService;
@Mock
private AccountRepository accountRepository;
@Captor
private ArgumentCaptor<Account> captor;
@Test
public void test() {
when(accountRepository.save(captor.capture())).thenReturn(...);
Account captorValue = captor.getValue();
accountService.createAccount(...);
// verify(accountRepository).save(captor.capture()); // you can also capture here and then captor.getValue()
assertEquals(AccountRole.USER.toString(), captorValue.getRole());
}
}
You can also create ArgumentCaptor
direct in test method:
ArgumentCaptor<Account> captor = ArgumentCaptor.forClass(Account.class);
Answered By - Georgii Lvov
Answer Checked By - David Marino (JavaFixing Volunteer)