Commit 67bff2ac authored by Ashok Kumar K's avatar Ashok Kumar K

Added 3 date related apis and few component and integration test cases

parent 65f2dd55
package com.nisum.ecomcustomer.controller;
import com.nisum.ecomcustomer.model.Customer;
import com.nisum.ecomcustomer.model.CustomerType;
import com.nisum.ecomcustomer.service.CustomerService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.format.annotation.DateTimeFormat;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.validation.annotation.Validated;
......@@ -11,6 +13,7 @@ import org.springframework.web.bind.annotation.*;
import javax.validation.Valid;
import javax.validation.constraints.Email;
import javax.validation.constraints.NotNull;
import java.time.LocalDate;
import java.util.List;
@RestController
......@@ -61,6 +64,23 @@ public class CustomerController {
return ResponseEntity.ok(customerService.getCustomerByLastName(lName));
}
@GetMapping("/type/{type}")
public ResponseEntity<List<Customer>> getCustomersByCustomerType(@PathVariable("type") int type) {
CustomerType customerType = CustomerType.of(type);
return ResponseEntity.ok(customerService.getCustomersByCustomerType(customerType));
}
@GetMapping("/registered/on")
public ResponseEntity<List<Customer>> getRegisteredCustomersOnDate(@RequestParam("onDate") @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate onDate) {
return ResponseEntity.ok(customerService.getRegisteredCustomersOnDate(onDate));
}
@GetMapping("/registered/between")
public ResponseEntity<List<Customer>> getRegisteredCustomersBetweenDates(@RequestParam("fromDate") @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate fromDate,
@RequestParam("toDate") @DateTimeFormat(iso = DateTimeFormat.ISO.DATE) LocalDate toDate) {
return ResponseEntity.ok(customerService.getRegisteredCustomersBetweenDates(fromDate, toDate));
}
@DeleteMapping("/id/{id}")
public ResponseEntity<Void> deleteById(@PathVariable Long id) {
customerService.deleteById(id);
......
......@@ -31,6 +31,11 @@ public class CustomerServiceExceptionHandler {
return buildErrorResponseEntity(ex.getLocalizedMessage(), HttpStatus.CONFLICT, httpServletRequest);
}
@ExceptionHandler(InvalidDateRangeException.class)
public ResponseEntity<ErrorResponse> handleInvalidDateRangeException(InvalidDateRangeException ex, HttpServletRequest httpServletRequest) {
return buildErrorResponseEntity(ex.getLocalizedMessage(), HttpStatus.BAD_REQUEST, httpServletRequest);
}
@ExceptionHandler(MethodArgumentNotValidException.class)
public ResponseEntity<Object> handleMethodArgumentNotValidException(MethodArgumentNotValidException ex, HttpServletRequest httpServletRequest) {
ErrorResponse errorResponse = buildErrorResponse("Invalid payload or params", HttpStatus.BAD_REQUEST, httpServletRequest);
......@@ -52,6 +57,11 @@ public class CustomerServiceExceptionHandler {
return new ResponseEntity<>(errorResponse, HttpStatus.BAD_REQUEST);
}
@ExceptionHandler(IllegalArgumentException.class)
public ResponseEntity<ErrorResponse> handleIllegalArgumentException(IllegalArgumentException ex, HttpServletRequest httpServletRequest) {
return buildErrorResponseEntity(ex.getLocalizedMessage(), HttpStatus.BAD_REQUEST, httpServletRequest);
}
@ExceptionHandler(Exception.class)
public ResponseEntity<ErrorResponse> handleException(Exception ex, HttpServletRequest httpServletRequest) {
return buildErrorResponseEntity(ex.getLocalizedMessage(), HttpStatus.INTERNAL_SERVER_ERROR, httpServletRequest);
......
package com.nisum.ecomcustomer.exceptions;
public class InvalidDateRangeException extends RuntimeException {
public InvalidDateRangeException() {
super("invalid date range");
}
public InvalidDateRangeException(String message) {
super(message);
}
public InvalidDateRangeException(String message, Throwable cause) {
super(message, cause);
}
}
......@@ -27,7 +27,7 @@ public enum AddressType {
case "bill":
return AddressType.BILLING;
default:
throw new IllegalArgumentException(value +" can't be converted to type AddressType");
throw new IllegalArgumentException(value +" isn't mapped to any AddressType");
}
}
}
......@@ -27,7 +27,7 @@ public enum CustomerType {
case 1:
return CustomerType.LOYAL;
default:
throw new IllegalArgumentException(value + " can't be converted to type CustomerType");
throw new IllegalArgumentException(value + " isn't mapped to any CustomerType");
}
}
}
package com.nisum.ecomcustomer.repository;
import com.nisum.ecomcustomer.model.Customer;
import com.nisum.ecomcustomer.model.CustomerType;
import org.springframework.data.mongodb.repository.MongoRepository;
import org.springframework.data.mongodb.repository.Query;
import java.time.LocalDate;
import java.util.List;
import java.util.Optional;
......@@ -16,8 +18,12 @@ public interface CustomerRepository extends MongoRepository<Customer, Long> {
List<Customer> findByLastNameIgnoreCase(String lName);
List<Customer> findByCustomerType(CustomerType customerType);
boolean existsByEmail(String email);
boolean existsByEmailIn(List<String> emails);
List<Customer> findByCreatedDate(LocalDate date);
}
package com.nisum.ecomcustomer.service;
import com.nisum.ecomcustomer.model.Customer;
import com.nisum.ecomcustomer.model.CustomerType;
import org.springframework.stereotype.Service;
import java.time.LocalDate;
import java.util.List;
@Service
......@@ -24,4 +26,10 @@ public interface CustomerService {
List<Customer> getCustomerByFirstName(String fName);
List<Customer> getCustomerByLastName(String lName);
List<Customer> getRegisteredCustomersOnDate(LocalDate onDate);
List<Customer> getRegisteredCustomersBetweenDates(LocalDate fromDate, LocalDate toDate);
List<Customer> getCustomersByCustomerType(CustomerType customerType);
}
......@@ -2,17 +2,23 @@ package com.nisum.ecomcustomer.service.impl;
import com.nisum.ecomcustomer.exceptions.CustomerNotFoundException;
import com.nisum.ecomcustomer.exceptions.EmailAlreadyRegisteredException;
import com.nisum.ecomcustomer.exceptions.InvalidDateRangeException;
import com.nisum.ecomcustomer.model.Customer;
import com.nisum.ecomcustomer.model.CustomerType;
import com.nisum.ecomcustomer.repository.CustomerRepository;
import com.nisum.ecomcustomer.service.CustomerService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;
import java.time.LocalDate;
import java.util.List;
import java.util.stream.Collectors;
import static org.springframework.data.mongodb.core.query.Criteria.where;
@Slf4j
@Service
public class CustomerServiceImpl implements CustomerService {
......@@ -77,6 +83,23 @@ public class CustomerServiceImpl implements CustomerService {
return customerRepository.findByLastNameIgnoreCase(lName);
}
@Override
public List<Customer> getCustomersByCustomerType(CustomerType customerType) {
return customerRepository.findByCustomerType(customerType);
}
@Override
public List<Customer> getRegisteredCustomersOnDate(LocalDate onDate) {
return customerRepository.findByCreatedDate(onDate);
}
@Override
public List<Customer> getRegisteredCustomersBetweenDates(LocalDate fromDate, LocalDate toDate) {
if (fromDate.isAfter(toDate)) throw new InvalidDateRangeException("invalid date range: fromDate can't be greater than toDate");
Query query = new Query(where("createdDate").gte(fromDate).lte(toDate));
return mongoTemplate.find(query, Customer.class);
}
@Override
public void deleteById(Long id) {
if (customerRepository.existsById(id)) customerRepository.deleteById(id);
......
......@@ -21,6 +21,7 @@ import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
import static org.hamcrest.Matchers.hasSize;
import static org.hamcrest.Matchers.is;
......@@ -79,7 +80,7 @@ class CustomerControllerTest {
.content(objectMapper.writeValueAsString(customersRequestObj))
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isCreated())
.andExpect(jsonPath("$", hasSize(2)))
.andExpect(jsonPath("$", hasSize(3)))
.andReturn();
}
......@@ -87,7 +88,7 @@ class CustomerControllerTest {
void registerCustomers_throwsEmailAlreadyRegisteredException_409() throws Exception {
List<Customer> customersRequestObj = getCustomerRequestObjectsList();
when(customerService.registerAll(customersRequestObj)).thenThrow(new EmailAlreadyRegisteredException());
MvcResult result = mockMvc.perform(post("/customer/registerAll")
mockMvc.perform(post("/customer/registerAll")
.content(objectMapper.writeValueAsString(customersRequestObj))
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isConflict())
......@@ -133,7 +134,7 @@ class CustomerControllerTest {
when(customerService.getAllCustomers()).thenReturn(getCustomerResponseObjectsList());
mockMvc.perform(get("/customer/"))
.andExpect(status().isOk())
.andExpect(jsonPath("$", hasSize(2)))
.andExpect(jsonPath("$", hasSize(3)))
.andReturn();
}
......@@ -181,6 +182,38 @@ class CustomerControllerTest {
void getCustomersByLastName() {
}
@Test
void getCustomersByCustomerType_returnsCustomers_200() throws Exception {
int loyalValue = CustomerType.LOYAL.getValue();
when(customerService.getCustomersByCustomerType(CustomerType.LOYAL)).
thenReturn(getCustomerResponseObjectsList().stream()
.filter(customer -> customer.getCustomerType().getValue() == loyalValue)
.collect(Collectors.toList()));
mockMvc.perform(get("/customer/type/" + loyalValue))
.andExpect(status().isOk())
.andExpect(jsonPath("$", hasSize(2)))
.andExpect(jsonPath("$[0].customerType", is(loyalValue)))
.andExpect(jsonPath("$[1].customerType", is(loyalValue)))
.andReturn();
}
@Test
void getCustomersByCustomerType_throwsIllegalArgumentException_400() throws Exception {
int typeValue = 3;
mockMvc.perform(get("/customer/type/" + typeValue))
.andExpect(status().isBadRequest())
.andReturn();
}
@Test
void getRegisteredCustomersOnDate() {
}
@Test
void getRegisteredCustomersBetweenDates() {
}
@Test
void deleteById_returnsNoContent_204() throws Exception {
doNothing().when(customerService).deleteById(1L);
......@@ -254,7 +287,10 @@ class CustomerControllerTest {
Customer customer1 = getCustomerRequestObject();
Customer customer2 = getCustomerRequestObject();
customer2.setEmail("anandk@nisum.com");
return Arrays.asList(customer1, customer2);
Customer customer3 = getCustomerRequestObject();
customer3.setEmail("anandk1@nisum.com");
customer3.setCustomerType(CustomerType.REGULAR);
return Arrays.asList(customer1, customer2, customer3);
}
private List<Customer> getCustomerResponseObjectsList() {
......@@ -273,4 +309,5 @@ class CustomerControllerTest {
String responseAsString = result.getResponse().getContentAsString();
return objectMapper.readValue(responseAsString, targetClass);
}
}
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment