package ca.intelliware.ihtsdo.mlds.repository; import static org.hamcrest.CoreMatchers.hasItem; import static org.hamcrest.CoreMatchers.not; import static org.hamcrest.Matchers.is; import static org.junit.Assert.assertThat; import java.util.Arrays; import java.util.HashSet; import java.util.List; import java.util.Random; import javax.annotation.Resource; import javax.persistence.EntityManager; import javax.transaction.Transactional; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.boot.test.SpringApplicationConfiguration; import org.springframework.data.domain.Page; import org.springframework.data.domain.PageRequest; import org.springframework.data.domain.Pageable; import org.springframework.test.context.ActiveProfiles; import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; import org.springframework.test.context.web.WebAppConfiguration; import com.google.common.collect.Lists; import com.google.common.collect.Sets; import ca.intelliware.ihtsdo.mlds.domain.Affiliate; import ca.intelliware.ihtsdo.mlds.domain.AffiliateDetails; import ca.intelliware.ihtsdo.mlds.domain.Application; import ca.intelliware.ihtsdo.mlds.domain.ApprovalState; import ca.intelliware.ihtsdo.mlds.domain.ExtensionApplication; import ca.intelliware.ihtsdo.mlds.domain.MailingAddress; import ca.intelliware.ihtsdo.mlds.domain.Member; import ca.intelliware.ihtsdo.mlds.domain.PrimaryApplication; import ca.intelliware.ihtsdo.mlds.domain.StandingState; import ca.intelliware.ihtsdo.mlds.search.AngularTranslateServiceSetup; @RunWith(SpringJUnit4ClassRunner.class) @SpringApplicationConfiguration(classes = ca.intelliware.ihtsdo.mlds.Application.class) @WebAppConfiguration @ActiveProfiles("dev") @Transactional public class AffiliateRepositoryTest { @Resource EntityManager entityManager; @Resource AffiliateRepository affiliateRepository; @Resource MemberRepository memberRepository; @Resource CountryRepository countryRepository; Random random = new Random(); List<Affiliate> affiliates = Lists.newArrayList(); Member ihtsdo; Member sweden; Member belgium; private Pageable pageable; private String uniqueKey; @Before public void setUp() { ihtsdo = memberRepository.findOneByKey(Member.KEY_IHTSDO); sweden = memberRepository.findOneByKey("SE"); belgium = memberRepository.findOneByKey("BE"); pageable = new PageRequest(0, 10); uniqueKey = ""+System.currentTimeMillis(); } @Before public void setupTranslations() { new AngularTranslateServiceSetup().setup(); } @Test public void findByCheckByIdShouldMatchExtension() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.IN_GOOD_STANDING, ihtsdo, "test"+uniqueKey+"@email.com"); withExtensionApplication(affiliate, sweden, ApprovalState.APPROVED); persistAffiliate(affiliate); flush(); // test no-match based on email Page<Affiliate> result = affiliateRepository.findForCheck(AffiliateRepository.AFFILIATE_ID_OPTIONAL_VALUE, sweden, "UNKNOWN"+uniqueKey, pageable); assertThat(result.getNumberOfElements(), is(0)); // test match based on email result = affiliateRepository.findForCheck(AffiliateRepository.AFFILIATE_ID_OPTIONAL_VALUE, sweden, uniqueKey, pageable); assertThat(result.getNumberOfElements(), is(1)); } @Test public void findByUsersAndStandingStateInAndApprovedPrimaryApplication() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.IN_GOOD_STANDING, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.APPROVED); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedPrimaryApplication(Arrays.asList(StandingState.IN_GOOD_STANDING)); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, hasItem(affiliate)); } @Test public void findByUsersAndStandingStateInAndApprovedPrimaryApplicationShouldFailForNotStandingStateMatch() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.INVOICE_SENT, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.APPROVED); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedPrimaryApplication(Arrays.asList(StandingState.IN_GOOD_STANDING)); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, not(hasItem(affiliate))); } @Test public void findByUsersAndStandingStateInAndApprovedPrimaryApplicationShouldFailForNonApproved() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.IN_GOOD_STANDING, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.REVIEW_REQUESTED); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedPrimaryApplication(Arrays.asList(StandingState.IN_GOOD_STANDING)); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, not(hasItem(affiliate))); } @Test public void findByUsersAndStandingStateInAndApprovedHomeMembership() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.IN_GOOD_STANDING, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.APPROVED); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedHomeMembership(Arrays.asList(StandingState.IN_GOOD_STANDING), sweden); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, hasItem(affiliate)); } @Test public void findByUsersAndStandingStateInAndApprovedHomeMembershipShouldIgnoreExtension() throws Exception { Affiliate affiliateIhtsdo = withAffiliateUser(StandingState.IN_GOOD_STANDING, ihtsdo, "test"+uniqueKey+"@email.com"); withExtensionApplication(affiliateIhtsdo, sweden, ApprovalState.APPROVED); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedHomeMembership(Arrays.asList(StandingState.IN_GOOD_STANDING), sweden); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, not(hasItem(affiliateIhtsdo))); } @Test public void findByUsersAndStandingStateInAndApprovedHomeMembershipShouldMatchStandingState() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.DEACTIVATION_PENDING, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.APPROVED); persistAffiliate(affiliate); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedHomeMembership(Arrays.asList(StandingState.IN_GOOD_STANDING), sweden); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, not(hasItem(affiliate))); } @Test public void findByUsersAndStandingStateInAndApprovedHomeMembershipShouldMatchApprovalState() throws Exception { Affiliate affiliate = withAffiliateUser(StandingState.IN_GOOD_STANDING, sweden, "test"+uniqueKey+"@email.com"); withPrimaryApplication(affiliate, sweden, ApprovalState.REJECTED); persistAffiliate(affiliate); flush(); Iterable<Affiliate> elements = affiliateRepository.findByUsersAndStandingStateInAndApprovedHomeMembership(Arrays.asList(StandingState.IN_GOOD_STANDING), sweden); HashSet<Affiliate> matches = Sets.newHashSet(elements); assertThat(matches, not(hasItem(affiliate))); } private void persistAffiliate(Affiliate affiliate) { affiliateRepository.save(affiliate); } private Affiliate withAffiliateUser(StandingState standingState, Member homeMember, String email) { Affiliate affiliate = new Affiliate(); affiliate.setHomeMember(homeMember); affiliate.setCreator(email); AffiliateDetails affiliateDetails = new AffiliateDetails(); affiliateDetails.setEmail(email); affiliate.setAffiliateDetails(affiliateDetails); affiliate.setStandingState(standingState); entityManager.persist(affiliate.getAffiliateDetails()); affiliateRepository.save(affiliate); return affiliate; } private Application withExtensionApplication(Affiliate affiliate, Member member, ApprovalState approvalState) { ExtensionApplication application = new ExtensionApplication(); application.setMember(member); application.setApprovalState(approvalState); entityManager.persist(application); affiliate.addApplication(application); affiliateRepository.save(affiliate); return application; } private Application withPrimaryApplication(Affiliate affiliate, Member member, ApprovalState approvalState) { PrimaryApplication application = new PrimaryApplication(); application.setMember(member); application.setApprovalState(approvalState); entityManager.persist(application); affiliate.addApplication(application); affiliate.setApplication(application); affiliateRepository.save(affiliate); return application; } /** * flush to JPA + Lucene. JPA queries trigger a JPA flush, but Hibernate Search * only flushes on TX commit by default. But are using a TX rollback test strategy, so we * need to flush Lucene manually. */ private void flush() { entityManager.flush(); } Affiliate makeAffiliate() { Affiliate affiliate = new Affiliate(); affiliate.setAffiliateDetails(new AffiliateDetails()); affiliate.getAffiliateDetails().setFirstName(randomString("firstName"));; affiliate.getAffiliateDetails().setLastName(randomString("lastName"));; affiliate.getAffiliateDetails().setAddress(new MailingAddress()); affiliate.setHomeMember(ihtsdo); entityManager.persist(affiliate.getAffiliateDetails()); affiliateRepository.save(affiliate); return affiliate; } private String randomString(String prefix) { return prefix + random.nextLong(); } }