implemented more AssetDTO+ShareDTO tests and fixed but in ShareDTO

This commit is contained in:
Michael Hoennig 2019-04-28 14:08:57 +02:00
parent 2cd92d4e2c
commit 5835f15cd9
10 changed files with 355 additions and 159 deletions

View File

@ -58,6 +58,11 @@ public class Share implements Serializable {
return id; return id;
} }
public Share id(final Long id) {
this.id = id;
return this;
}
public void setId(Long id) { public void setId(Long id) {
this.id = id; this.id = id;
} }

View File

@ -150,17 +150,17 @@ public class AssetDTO implements Serializable, AccessMappings {
} }
@JsonComponent @JsonComponent
public static class AssetJsonSerializer extends JsonSerializerWithAccessFilter<AssetDTO> { public static class JsonSerializer extends JsonSerializerWithAccessFilter<AssetDTO> {
public AssetJsonSerializer(final ApplicationContext ctx) { public JsonSerializer(final ApplicationContext ctx) {
super(ctx); super(ctx);
} }
} }
@JsonComponent @JsonComponent
public static class AssetJsonDeserializer extends JsonDeserializerWithAccessFilter<AssetDTO> { public static class JsonDeserializer extends JsonDeserializerWithAccessFilter<AssetDTO> {
public AssetJsonDeserializer(final ApplicationContext ctx) { public JsonDeserializer(final ApplicationContext ctx) {
super(ctx); super(ctx);
} }
} }

View File

@ -3,10 +3,9 @@ package org.hostsharing.hsadminng.service.dto;
import org.hostsharing.hsadminng.domain.enumeration.ShareAction; import org.hostsharing.hsadminng.domain.enumeration.ShareAction;
import org.hostsharing.hsadminng.service.MembershipService; import org.hostsharing.hsadminng.service.MembershipService;
import org.hostsharing.hsadminng.service.ShareService; import org.hostsharing.hsadminng.service.ShareService;
import org.hostsharing.hsadminng.service.accessfilter.AccessFor; import org.hostsharing.hsadminng.service.accessfilter.*;
import org.hostsharing.hsadminng.service.accessfilter.ParentId; import org.springframework.boot.jackson.JsonComponent;
import org.hostsharing.hsadminng.service.accessfilter.Role; import org.springframework.context.ApplicationContext;
import org.hostsharing.hsadminng.service.accessfilter.SelfId;
import javax.validation.constraints.NotNull; import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size; import javax.validation.constraints.Size;
@ -17,7 +16,7 @@ import java.util.Objects;
/** /**
* A DTO for the Share entity. * A DTO for the Share entity.
*/ */
public class ShareDTO implements Serializable { public class ShareDTO implements Serializable, AccessMappings {
@SelfId(resolver = ShareService.class) @SelfId(resolver = ShareService.class)
@AccessFor(read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT}) @AccessFor(read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT})
@ -40,14 +39,14 @@ public class ShareDTO implements Serializable {
private Integer quantity; private Integer quantity;
@Size(max = 160) @Size(max = 160)
@AccessFor(init = Role.ADMIN, read = Role.SUPPORTER) @AccessFor(init = Role.ADMIN, update = Role.ADMIN, read = Role.SUPPORTER)
private String remark; private String remark;
@ParentId(resolver = MembershipService.class) @ParentId(resolver = MembershipService.class)
@AccessFor(init = Role.ADMIN, read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT}) @AccessFor(init = Role.ADMIN, read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT})
private Long membershipId; private Long membershipId;
@AccessFor(read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT}) @AccessFor(update = Role.IGNORED, read = {Role.CONTRACTUAL_CONTACT, Role.FINANCIAL_CONTACT})
private String membershipDisplayLabel; private String membershipDisplayLabel;
public Long getId() { public Long getId() {
@ -145,7 +144,23 @@ public class ShareDTO implements Serializable {
", quantity=" + getQuantity() + ", quantity=" + getQuantity() +
", remark='" + getRemark() + "'" + ", remark='" + getRemark() + "'" +
", membership=" + getMembershipId() + ", membership=" + getMembershipId() +
", membership='" + getMembershipDisplayLabel() + "'" + ", membershipDisplayLabel='" + getMembershipDisplayLabel() + "'" +
"}"; "}";
} }
@JsonComponent
public static class JsonSerializer extends JsonSerializerWithAccessFilter<ShareDTO> {
public JsonSerializer(final ApplicationContext ctx) {
super(ctx);
}
}
@JsonComponent
public static class JsonDeserializer extends JsonDeserializerWithAccessFilter<ShareDTO> {
public JsonDeserializer(final ApplicationContext ctx) {
super(ctx);
}
}
} }

View File

@ -1,9 +1,10 @@
package org.hostsharing.hsadminng.service.util; package org.hostsharing.hsadminng.service.util;
import org.apache.commons.lang3.RandomStringUtils; import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.RandomUtils;
/** /**
* Utility class for generating random Strings. * Utility class for generating random Values.
*/ */
public final class RandomUtil { public final class RandomUtil {
@ -38,4 +39,14 @@ public final class RandomUtil {
public static String generateResetKey() { public static String generateResetKey() {
return RandomStringUtils.randomNumeric(DEF_COUNT); return RandomStringUtils.randomNumeric(DEF_COUNT);
} }
/**
* Generate a random enum value for a given enum type.
*
* @return the generated enum value
*/
public static <E extends Enum<E>> E generateEnumValue(final Class<E> enumType) {
final E[] enumValues = enumType.getEnumConstants();
return enumValues[RandomUtils.nextInt(0, enumValues.length-1)];
}
} }

View File

@ -1,12 +1,13 @@
package org.hostsharing.hsadminng.service.dto; package org.hostsharing.hsadminng.service.dto;
import org.apache.commons.lang3.RandomUtils; import org.apache.commons.lang3.RandomUtils;
import org.hostsharing.hsadminng.service.accessfilter.AccessFor; import org.hostsharing.hsadminng.service.accessfilter.*;
import org.hostsharing.hsadminng.service.accessfilter.Role;
import org.hostsharing.hsadminng.service.util.ReflectionUtil; import org.hostsharing.hsadminng.service.util.ReflectionUtil;
import org.junit.Test; import org.junit.Test;
import org.springframework.boot.jackson.JsonComponent;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.lang.reflect.Modifier;
import java.util.HashSet; import java.util.HashSet;
import java.util.Objects; import java.util.Objects;
import java.util.Set; import java.util.Set;
@ -15,6 +16,7 @@ import java.util.stream.Collectors;
import static org.apache.commons.lang3.StringUtils.removeEnd; import static org.apache.commons.lang3.StringUtils.removeEnd;
import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.fail;
/** /**
* Usually base classes for unit tests are not a good idea, but because * Usually base classes for unit tests are not a good idea, but because
@ -60,6 +62,23 @@ public abstract class AccessMappingsUnitTestBase<D> {
assertThat(dtoWithoutId.hashCode()).isEqualTo(Objects.hashCode(null)); assertThat(dtoWithoutId.hashCode()).isEqualTo(Objects.hashCode(null));
} }
@Test
public void shouldImplementAccessMappings() {
assertThat(getDtoClass().getInterfaces()).as("must implement " + AccessMappings.class).contains(AccessMappings.class);
}
@Test
public void shouldImplementSerializer() {
shouldImplementJsonComponent(JsonSerializerWithAccessFilter.class);
}
@Test
public void shouldImplementDeserializer() {
shouldImplementJsonComponent(JsonDeserializerWithAccessFilter.class);
}
// --- only test fixture below ---
protected abstract D createSampleDto(final Long id); protected abstract D createSampleDto(final Long id);
protected abstract D createRandomDto(final Long id); protected abstract D createRandomDto(final Long id);
@ -174,4 +193,26 @@ public abstract class AccessMappingsUnitTestBase<D> {
private boolean isJHipsterToStringUsingQuotes(final Field field) { private boolean isJHipsterToStringUsingQuotes(final Field field) {
return !Number.class.isAssignableFrom(field.getType()) && !Boolean.class.isAssignableFrom(field.getType()); return !Number.class.isAssignableFrom(field.getType()) && !Boolean.class.isAssignableFrom(field.getType());
} }
private void shouldImplementJsonComponent(final Class<?> expectedSuperclass) {
final Class<D> dtoClass = getDtoClass();
for (Class<?> declaredClass: dtoClass.getDeclaredClasses()) {
if (expectedSuperclass.isAssignableFrom(declaredClass) ) {
assertThat( declaredClass.isAnnotationPresent(JsonComponent.class) )
.as(declaredClass + " requires @" + JsonComponent.class.getSimpleName()).isTrue();
assertThat( ReflectionUtil.determineGenericClassParameter(declaredClass, expectedSuperclass, 0))
.as(declaredClass + " must resolve generic parameter of " + expectedSuperclass + " to type of DTO").isEqualTo(dtoClass);
assertThat(Modifier.isPublic(declaredClass.getModifiers()) ).as(declaredClass + " must be public").isTrue();
assertThat(Modifier.isStatic(declaredClass.getModifiers()) ).as(declaredClass + " must be static").isTrue();
assertThat(Modifier.isFinal(declaredClass.getModifiers()) ).as(declaredClass + " must not be final").isFalse();
assertThat(Modifier.isAbstract(declaredClass.getModifiers()) ).as(declaredClass + " must not be abstract").isFalse();
return;
}
}
fail("no " + expectedSuperclass + " defined for " + dtoClass);
}
private Class<D> getDtoClass() {
return ReflectionUtil.determineGenericClassParameter(this.getClass(), AccessMappingsUnitTestBase.class, 0);
}
} }

View File

@ -50,8 +50,8 @@ import static org.mockito.BDDMockito.given;
CustomerMapperImpl.class, CustomerMapperImpl.class,
MembershipMapperImpl.class, MembershipMapperImpl.class,
AssetMapperImpl.class, AssetMapperImpl.class,
AssetDTO.AssetJsonSerializer.class, AssetDTO.JsonSerializer.class,
AssetDTO.AssetJsonDeserializer.class AssetDTO.JsonDeserializer.class
}) })
@RunWith(SpringRunner.class) @RunWith(SpringRunner.class)
public class AssetDTOIntTest { public class AssetDTOIntTest {

View File

@ -4,6 +4,7 @@ import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.RandomUtils; import org.apache.commons.lang3.RandomUtils;
import org.hostsharing.hsadminng.domain.enumeration.AssetAction; import org.hostsharing.hsadminng.domain.enumeration.AssetAction;
import org.hostsharing.hsadminng.service.accessfilter.Role; import org.hostsharing.hsadminng.service.accessfilter.Role;
import org.hostsharing.hsadminng.service.util.RandomUtil;
import org.junit.Test; import org.junit.Test;
import java.math.BigDecimal; import java.math.BigDecimal;
@ -59,19 +60,18 @@ public class AssetDTOUnitTest extends AccessMappingsUnitTestBase<AssetDTO> {
return dto; return dto;
} }
@Override @Override
public AssetDTO createRandomDto(final Long id) { public AssetDTO createRandomDto(final Long id) {
final AssetDTO dto = new AssetDTO(); final AssetDTO dto = new AssetDTO();
dto.setId(id); dto.setId(id);
final LocalDate randomDate = LocalDate.parse("2000-12-07").plusDays(RandomUtils.nextInt(1, 999)); final LocalDate randomDate = LocalDate.parse("2000-12-07").plusDays(RandomUtils.nextInt(1, 999));
dto.setDocumentDate(randomDate); dto.setDocumentDate(randomDate);
dto.setAmount(new BigDecimal("512.01")); dto.setAmount(new BigDecimal(RandomUtils.nextDouble()));
dto.setAction(AssetAction.PAYMENT); dto.setAction(RandomUtil.generateEnumValue(AssetAction.class));
dto.setRemark("Some Remark"); dto.setRemark(RandomStringUtils.randomAlphanumeric(20));
dto.setValueDate(randomDate.plusDays(RandomUtils.nextInt(1, 99))); dto.setValueDate(randomDate.plusDays(RandomUtils.nextInt(1, 99)));
dto.setMembershipId(RandomUtils.nextLong()); dto.setMembershipId(RandomUtils.nextLong());
dto.setMembershipDisplayLabel(RandomStringUtils.randomAlphabetic(20)); dto.setMembershipDisplayLabel("The Membership #" + dto.getMembershipId());
return dto; return dto;
} }
} }

View File

@ -0,0 +1,210 @@
package org.hostsharing.hsadminng.service.dto;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.apache.commons.lang3.RandomUtils;
import org.hostsharing.hsadminng.domain.Customer;
import org.hostsharing.hsadminng.domain.Membership;
import org.hostsharing.hsadminng.domain.Share;
import org.hostsharing.hsadminng.domain.enumeration.ShareAction;
import org.hostsharing.hsadminng.repository.CustomerRepository;
import org.hostsharing.hsadminng.repository.MembershipRepository;
import org.hostsharing.hsadminng.repository.ShareRepository;
import org.hostsharing.hsadminng.service.MembershipValidator;
import org.hostsharing.hsadminng.service.ShareService;
import org.hostsharing.hsadminng.service.ShareValidator;
import org.hostsharing.hsadminng.service.accessfilter.JSonBuilder;
import org.hostsharing.hsadminng.service.accessfilter.Role;
import org.hostsharing.hsadminng.service.mapper.CustomerMapperImpl;
import org.hostsharing.hsadminng.service.mapper.MembershipMapperImpl;
import org.hostsharing.hsadminng.service.mapper.ShareMapper;
import org.hostsharing.hsadminng.service.mapper.ShareMapperImpl;
import org.hostsharing.hsadminng.web.rest.errors.BadRequestAlertException;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.junit.MockitoJUnit;
import org.mockito.junit.MockitoRule;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.json.JsonTest;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.boot.test.mock.mockito.MockBean;
import org.springframework.test.context.junit4.SpringRunner;
import javax.persistence.EntityManager;
import java.io.IOException;
import java.time.LocalDate;
import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.catchThrowable;
import static org.hostsharing.hsadminng.service.accessfilter.MockSecurityContext.givenAuthenticatedUser;
import static org.hostsharing.hsadminng.service.accessfilter.MockSecurityContext.givenUserHavingRole;
import static org.junit.Assert.assertEquals;
import static org.mockito.BDDMockito.given;
@JsonTest
@SpringBootTest(classes = {
CustomerMapperImpl.class,
MembershipMapperImpl.class,
ShareMapperImpl.class,
ShareDTO.JsonSerializer.class,
ShareDTO.JsonDeserializer.class
})
@RunWith(SpringRunner.class)
public class ShareDTOIntTest {
private static final Long SOME_CUSTOMER_ID = RandomUtils.nextLong(100, 199);
private static final Integer SOME_CUSTOMER_REFERENCE = 10001;
private static final String SOME_CUSTOMER_PREFIX = "abc";
private static final String SOME_CUSTOMER_NAME = "Some Customer Name";
private static final Customer SOME_CUSTOMER = new Customer().id(SOME_CUSTOMER_ID)
.reference(SOME_CUSTOMER_REFERENCE).prefix(SOME_CUSTOMER_PREFIX).name(SOME_CUSTOMER_NAME);
private static final Long SOME_MEMBERSHIP_ID = RandomUtils.nextLong(200, 299);
private static final LocalDate SOME_MEMBER_FROM_DATE = LocalDate.parse("2000-12-06");
private static final Membership SOME_MEMBERSHIP = new Membership().id(SOME_MEMBERSHIP_ID)
.customer(SOME_CUSTOMER).memberFromDate(SOME_MEMBER_FROM_DATE);
private static final String SOME_MEMBERSHIP_DISPLAY_LABEL = "Some Customer Name [10001:abc] 2000-12-06 - ...";
private static final Long SOME_SHARE_ID = RandomUtils.nextLong(300, 399);
private static final Share SOME_SHARE = new Share().id(SOME_SHARE_ID).membership(SOME_MEMBERSHIP);
@Rule
public MockitoRule mockito = MockitoJUnit.rule();
@Autowired
private ObjectMapper objectMapper;
@Autowired
private ShareMapper shareMapper;
@MockBean
private ShareRepository shareRepository;
@MockBean
private ShareValidator shareValidator;
@MockBean
private CustomerRepository customerRepository;
@MockBean
private MembershipRepository membershipRepository;
@MockBean
private MembershipValidator membershipValidator;
@MockBean
private ShareService shareService;
@MockBean
private EntityManager em;
@Before
public void init() {
given(customerRepository.findById(SOME_CUSTOMER_ID)).willReturn(Optional.of(SOME_CUSTOMER));
given(membershipRepository.findById(SOME_MEMBERSHIP_ID)).willReturn(Optional.of(SOME_MEMBERSHIP));
given(shareRepository.findById(SOME_SHARE_ID)).willReturn((Optional.of(SOME_SHARE)));
}
@Test
public void shouldSerializePartiallyForFinancialCustomerContact() throws JsonProcessingException {
// given
givenAuthenticatedUser();
givenUserHavingRole(CustomerDTO.class, SOME_CUSTOMER_ID, Role.FINANCIAL_CONTACT);
final ShareDTO given = createSomeShareDTO(SOME_SHARE_ID);
// when
final String actual = objectMapper.writeValueAsString(given);
// then
given.setRemark(null);
assertEquals(createExpectedJSon(given), actual);
}
@Test
public void shouldSerializeCompletelyForSupporter() throws JsonProcessingException {
// given
givenAuthenticatedUser();
givenUserHavingRole(Role.SUPPORTER);
final ShareDTO given = createSomeShareDTO(SOME_SHARE_ID);
// when
final String actual = objectMapper.writeValueAsString(given);
// then
assertEquals(createExpectedJSon(given), actual);
}
@Test
public void shouldNotDeserializeForContractualCustomerContact() {
// given
givenAuthenticatedUser();
givenUserHavingRole(CustomerDTO.class, SOME_CUSTOMER_ID, Role.CONTRACTUAL_CONTACT);
final String json = new JSonBuilder()
.withFieldValue("id", SOME_SHARE_ID)
.withFieldValue("remark", "Updated Remark")
.toString();
// when
final Throwable actual = catchThrowable(() -> objectMapper.readValue(json, ShareDTO.class));
// then
assertThat(actual).isInstanceOfSatisfying(BadRequestAlertException.class, bre ->
assertThat(bre.getMessage()).isEqualTo("Update of field ShareDTO.remark prohibited for current user role CONTRACTUAL_CONTACT")
);
}
@Test
public void shouldDeserializeForAdminIfRemarkIsChanged() throws IOException {
// given
givenAuthenticatedUser();
givenUserHavingRole(Role.ADMIN);
final String json = new JSonBuilder()
.withFieldValue("id", SOME_SHARE_ID)
.withFieldValue("remark", "Updated Remark")
.toString();
// when
final ShareDTO actual = objectMapper.readValue(json, ShareDTO.class);
// then
final ShareDTO expected = new ShareDTO();
expected.setId(SOME_SHARE_ID);
expected.setMembershipId(SOME_MEMBERSHIP_ID);
expected.setRemark("Updated Remark");
expected.setMembershipDisplayLabel(SOME_MEMBERSHIP_DISPLAY_LABEL);
assertThat(actual).isEqualToIgnoringGivenFields(expected, "displayLabel");
}
// --- only test fixture below ---
private String createExpectedJSon(ShareDTO dto) {
return new JSonBuilder()
.withFieldValueIfPresent("id", dto.getId())
.withFieldValueIfPresent("documentDate", dto.getDocumentDate().toString())
.withFieldValueIfPresent("valueDate", dto.getValueDate().toString())
.withFieldValueIfPresent("action", dto.getAction().name())
.withFieldValueIfPresent("quantity", dto.getQuantity())
.withFieldValueIfPresent("remark", dto.getRemark())
.withFieldValueIfPresent("membershipId", dto.getMembershipId())
.withFieldValue("membershipDisplayLabel", dto.getMembershipDisplayLabel())
.toString();
}
private ShareDTO createSomeShareDTO(final long id) {
final ShareDTO given = new ShareDTO();
given.setId(id);
given.setAction(ShareAction.SUBSCRIPTION);
given.setQuantity(16);
given.setDocumentDate(LocalDate.parse("2019-04-27"));
given.setValueDate(LocalDate.parse("2019-04-28"));
given.setMembershipId(SOME_MEMBERSHIP_ID);
given.setRemark("Some Remark");
given.setMembershipDisplayLabel("Display Label for Membership #" + SOME_MEMBERSHIP_ID);
return given;
}
}

View File

@ -1,162 +1,75 @@
package org.hostsharing.hsadminng.service.dto; package org.hostsharing.hsadminng.service.dto;
import com.fasterxml.jackson.core.JsonGenerator; import org.apache.commons.lang3.RandomStringUtils;
import com.fasterxml.jackson.core.JsonParser; import org.apache.commons.lang3.RandomUtils;
import com.fasterxml.jackson.core.ObjectCodec;
import com.fasterxml.jackson.core.TreeNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.apache.commons.lang3.tuple.ImmutablePair;
import org.hostsharing.hsadminng.domain.enumeration.ShareAction; import org.hostsharing.hsadminng.domain.enumeration.ShareAction;
import org.hostsharing.hsadminng.service.CustomerService;
import org.hostsharing.hsadminng.service.MembershipService;
import org.hostsharing.hsadminng.service.accessfilter.JSonDeserializationWithAccessFilter;
import org.hostsharing.hsadminng.service.accessfilter.JSonSerializationWithAccessFilter;
import org.hostsharing.hsadminng.service.accessfilter.Role; import org.hostsharing.hsadminng.service.accessfilter.Role;
import org.hostsharing.hsadminng.web.rest.errors.BadRequestAlertException; import org.hostsharing.hsadminng.service.util.RandomUtil;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test; import org.junit.Test;
import org.mockito.Mock;
import org.mockito.junit.MockitoJUnit;
import org.mockito.junit.MockitoRule;
import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
import org.springframework.context.ApplicationContext;
import java.io.IOException;
import java.time.LocalDate; import java.time.LocalDate;
import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat; public class ShareDTOUnitTest extends AccessMappingsUnitTestBase<ShareDTO> {
import static org.assertj.core.api.Assertions.catchThrowable;
import static org.hostsharing.hsadminng.service.accessfilter.JSonBuilder.asJSon;
import static org.hostsharing.hsadminng.service.accessfilter.MockSecurityContext.givenAuthenticatedUser;
import static org.hostsharing.hsadminng.service.accessfilter.MockSecurityContext.givenUserHavingRole;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.BDDMockito.given;
import static org.mockito.Mockito.never;
import static org.mockito.Mockito.verify;
public class ShareDTOUnitTest { @Test
public void shouldHaveProperAccessForAdmin() {
private static final long SOME_MEMBERSHIP_ID = 12345L; initAccessFor(ShareDTO.class, Role.ADMIN).shouldBeExactlyFor(
private static final long SOME_CUSTOMER_ID = 1234L; "membershipId", "documentDate", "quantity", "action", "valueDate", "remark");
updateAccessFor(ShareDTO.class, Role.ADMIN).shouldBeExactlyFor("remark");
@Rule readAccessFor(ShareDTO.class, Role.ADMIN).shouldBeForAllFields();
public MockitoRule mockitoRule = MockitoJUnit.rule();
@Mock
private ApplicationContext ctx;
@Mock
private AutowireCapableBeanFactory autowireCapableBeanFactory;
@Mock
private JsonParser jsonParser;
@Mock
private JsonGenerator jsonGenerator;
@Mock
private ObjectCodec codec;
@Mock
private TreeNode treeNode;
@Mock
private CustomerService customerService;
@Mock
private MembershipService membershipService;
@Before
public void init() {
given(jsonParser.getCodec()).willReturn(codec);
given(ctx.getAutowireCapableBeanFactory()).willReturn(autowireCapableBeanFactory);
given(autowireCapableBeanFactory.createBean(CustomerService.class)).willReturn(customerService);
given(autowireCapableBeanFactory.createBean(MembershipService.class)).willReturn(membershipService);
given(customerService.findOne(SOME_CUSTOMER_ID)).willReturn(Optional.of(new CustomerDTO()));
given(membershipService.findOne(SOME_MEMBERSHIP_ID)).willReturn(Optional.of(new MembershipDTO().with(dto -> dto.setCustomerId(SOME_CUSTOMER_ID))));
} }
@Test @Test
public void adminShouldHaveRightToCreate() throws IOException { public void shouldHaveProperAccessForContractualContact() {
givenAuthenticatedUser(); initAccessFor(ShareDTO.class, Role.CONTRACTUAL_CONTACT).shouldBeForNothing();
givenUserHavingRole(null, null, Role.ADMIN); updateAccessFor(ShareDTO.class, Role.CONTRACTUAL_CONTACT).shouldBeForNothing();
givenJSonTree(asJSon(ImmutablePair.of("membershipId", SOME_MEMBERSHIP_ID))); readAccessFor(ShareDTO.class, Role.CONTRACTUAL_CONTACT).shouldBeExactlyFor(
"id", "membershipId", "documentDate", "quantity", "action", "valueDate", "membershipDisplayLabel");
// when
final ShareDTO actualDto = new JSonDeserializationWithAccessFilter<>(ctx, jsonParser, null, ShareDTO.class).deserialize();
// then
assertThat(actualDto.getMembershipId()).isEqualTo(SOME_MEMBERSHIP_ID);
} }
@Test @Test
public void contractualContactShouldNotHaveRightToCreate() throws IOException { public void shouldHaveNoAccessForTechnicalContact() {
givenAuthenticatedUser(); initAccessFor(ShareDTO.class, Role.TECHNICAL_CONTACT).shouldBeForNothing();
givenUserHavingRole(CustomerDTO.class, SOME_CUSTOMER_ID, Role.CONTRACTUAL_CONTACT); updateAccessFor(ShareDTO.class, Role.TECHNICAL_CONTACT).shouldBeForNothing();
givenJSonTree(asJSon(ImmutablePair.of("membershipId", ShareDTOUnitTest.SOME_MEMBERSHIP_ID))); readAccessFor(ShareDTO.class, Role.TECHNICAL_CONTACT).shouldBeForNothing();
// when
Throwable exception = catchThrowable(() -> new JSonDeserializationWithAccessFilter<>(ctx, jsonParser, null, ShareDTO.class).deserialize());
// then
assertThat(exception).isInstanceOfSatisfying(BadRequestAlertException.class, badRequestAlertException -> {
assertThat(badRequestAlertException.getParam()).isEqualTo("ShareDTO.membershipId");
assertThat(badRequestAlertException.getErrorKey()).isEqualTo("referencingProhibited");
});
} }
@Test @Test
public void financialContactShouldHaveRightToReadAllButRemark() throws IOException { public void shouldHaveNoAccessForNormalUsersWithinCustomerRealm() {
givenAuthenticatedUser(); initAccessFor(ShareDTO.class, Role.ANY_CUSTOMER_USER).shouldBeForNothing();
givenUserHavingRole(CustomerDTO.class, SOME_CUSTOMER_ID, Role.FINANCIAL_CONTACT); updateAccessFor(ShareDTO.class, Role.ANY_CUSTOMER_USER).shouldBeForNothing();
final ShareDTO givenDTO = createShareDto(); readAccessFor(ShareDTO.class, Role.ANY_CUSTOMER_USER).shouldBeForNothing();
// when
new JSonSerializationWithAccessFilter<>(ctx, jsonGenerator, null, givenDTO).serialize();
// then
verify(jsonGenerator).writeNumberField("id", givenDTO.getId());
verify(jsonGenerator).writeNumberField("membershipId", givenDTO.getMembershipId());
verify(jsonGenerator, never()).writeStringField(eq("remark"), anyString());
} }
@Test // --- only test fixture below ---
public void supporterShouldHaveRightToRead() throws IOException {
givenAuthenticatedUser();
givenUserHavingRole(null, null, Role.SUPPORTER);
final ShareDTO givenDTO = createShareDto();
// when @Override
new JSonSerializationWithAccessFilter<>(ctx, jsonGenerator, null, givenDTO).serialize(); public ShareDTO createSampleDto(final Long id) {
final ShareDTO dto = new ShareDTO();
// then dto.setId(id);
verify(jsonGenerator).writeNumberField("id", givenDTO.getId()); dto.setMembershipId(888L);
verify(jsonGenerator).writeNumberField("membershipId", givenDTO.getMembershipId()); dto.setAction(ShareAction.SUBSCRIPTION);
verify(jsonGenerator).writeStringField("remark", givenDTO.getRemark()); dto.setQuantity(3);
dto.setDocumentDate(LocalDate.parse("2019-04-22"));
dto.setValueDate(LocalDate.parse("2019-04-30"));
dto.setRemark("Some Remark");
dto.setMembershipDisplayLabel("The Membership #888");
return dto;
} }
// --- only fixture code below --- @Override
public ShareDTO createRandomDto(final Long id) {
private void givenJSonTree(String givenJSon) throws IOException { final ShareDTO dto = new ShareDTO();
given(codec.readTree(jsonParser)).willReturn(new ObjectMapper().readTree(givenJSon)); dto.setId(id);
dto.setMembershipId(RandomUtils.nextLong());
dto.setAction(RandomUtil.generateEnumValue(ShareAction.class));
dto.setQuantity(RandomUtils.nextInt());
final LocalDate randomDate = LocalDate.parse("2000-12-07").plusDays(RandomUtils.nextInt(1, 999));
dto.setDocumentDate(randomDate);
dto.setValueDate(randomDate.plusDays(RandomUtils.nextInt(1, 99)));
dto.setRemark(RandomStringUtils.randomAlphanumeric(20));
dto.setMembershipDisplayLabel("The Membership #" + dto.getMembershipId());
return dto;
} }
private ShareDTO createShareDto() {
final ShareDTO givenDTO = new ShareDTO();
givenDTO.setId(1234567L);
givenDTO.setMembershipId(SOME_MEMBERSHIP_ID);
givenDTO.setAction(ShareAction.SUBSCRIPTION);
givenDTO.setQuantity(3);
givenDTO.setDocumentDate(LocalDate.parse("2019-04-22"));
givenDTO.setMembershipDisplayLabel("2019-04-21"); // TODO: why is this not a LocalDate?
givenDTO.setValueDate(LocalDate.parse("2019-04-30"));
givenDTO.setRemark("Some Remark");
return givenDTO;
}
} }

View File

@ -161,6 +161,7 @@ public class ShareResourceIntTest {
// Create the Share // Create the Share
ShareDTO shareDTO = shareMapper.toDto(share); ShareDTO shareDTO = shareMapper.toDto(share);
shareDTO.setMembershipDisplayLabel(null);
restShareMockMvc.perform(post("/api/shares") restShareMockMvc.perform(post("/api/shares")
.contentType(TestUtil.APPLICATION_JSON_UTF8) .contentType(TestUtil.APPLICATION_JSON_UTF8)
.content(TestUtil.convertObjectToJsonBytes(shareDTO))) .content(TestUtil.convertObjectToJsonBytes(shareDTO)))