diff --git a/checkstyle.xml b/checkstyle.xml
deleted file mode 100644
index 4548f16..0000000
--- a/checkstyle.xml
+++ /dev/null
@@ -1,250 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/src/main/java/service/carsharing/mapper/CarMapper.java b/src/main/java/service/carsharing/mapper/CarMapper.java
index f266091..308801f 100644
--- a/src/main/java/service/carsharing/mapper/CarMapper.java
+++ b/src/main/java/service/carsharing/mapper/CarMapper.java
@@ -1,6 +1,7 @@
package service.carsharing.mapper;
import org.mapstruct.Mapper;
+import org.mapstruct.MappingTarget;
import service.carsharing.config.MapperConfig;
import service.carsharing.dto.cars.CarRequestDto;
import service.carsharing.dto.cars.CarResponseDto;
@@ -11,4 +12,6 @@ public interface CarMapper {
Car toModel(CarRequestDto requestDto);
CarResponseDto toDto(Car car);
+
+ void updateCar(CarRequestDto requestDto, @MappingTarget Car car);
}
diff --git a/src/main/java/service/carsharing/service/impl/CarServiceImpl.java b/src/main/java/service/carsharing/service/impl/CarServiceImpl.java
index f4cad4b..eb45072 100644
--- a/src/main/java/service/carsharing/service/impl/CarServiceImpl.java
+++ b/src/main/java/service/carsharing/service/impl/CarServiceImpl.java
@@ -2,7 +2,6 @@
import jakarta.persistence.EntityNotFoundException;
import java.util.List;
-import java.util.Optional;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Service;
@@ -34,22 +33,23 @@ public List getAllCars(Pageable pageable) {
@Override
public CarResponseDto getCar(Long id) {
- Optional carById = carRepository.findByIdAndDeletedFalse(id);
- if (carById.isPresent()) {
- return carMapper.toDto(carById.get());
- }
- throw new EntityNotFoundException("Can't find car with id: " + id);
+ return carMapper.toDto(getCarById(id));
}
@Override
public CarResponseDto updateCar(Long id, CarRequestDto requestDto) {
- carRepository.findByIdAndDeletedFalse(id).orElseThrow(
- () -> new EntityNotFoundException("Can't find car with id: " + id));
- return carMapper.toDto(carRepository.save(carMapper.toModel(requestDto)));
+ Car car = getCarById(id);
+ carMapper.updateCar(requestDto, car);
+ return carMapper.toDto(carRepository.save(car));
}
@Override
public void deleteCar(Long id) {
carRepository.softDelete(id);
}
+
+ private Car getCarById(Long id) {
+ return carRepository.findByIdAndDeletedFalse(id).orElseThrow(
+ () -> new EntityNotFoundException("Can't find car with id: " + id));
+ }
}
diff --git a/src/main/java/service/carsharing/service/impl/RentalServiceImpl.java b/src/main/java/service/carsharing/service/impl/RentalServiceImpl.java
index 4690906..0cf61b0 100644
--- a/src/main/java/service/carsharing/service/impl/RentalServiceImpl.java
+++ b/src/main/java/service/carsharing/service/impl/RentalServiceImpl.java
@@ -25,6 +25,8 @@
@RequiredArgsConstructor
@Service
public class RentalServiceImpl implements RentalService {
+ private static final Integer MIN_REQUIRED_CAR_AVAILABLE = 1;
+
private final RentalRepository rentalRepository;
private final UserRepository userRepository;
private final CarRepository carRepository;
@@ -39,13 +41,7 @@ public RentalResponseDto addNewRental(RentalRequestDto requestDto) {
throw new RuntimeException("You have expired payments, denied access");
}
Car car = getCarById(requestDto.carId());
- if (car.getInventory() < 1) {
- notificationService.sendNotification(requestDto.userId(),
- "There is no free available car with id: "
- + requestDto.carId());
- throw new RuntimeException("There is no free available car with id: "
- + requestDto.carId());
- }
+ checkIsExistsAvailableCar(requestDto, car);
car.setInventory(car.getInventory() - 1);
carRepository.save(car);
RentalResponseDto responseDto = rentalMapper.toDto(rentalRepository
@@ -113,6 +109,16 @@ private boolean canBorrow(Long userId) {
return expiredState.isEmpty();
}
+ private void checkIsExistsAvailableCar(RentalRequestDto requestDto, Car car) {
+ if (car.getInventory() < MIN_REQUIRED_CAR_AVAILABLE) {
+ notificationService.sendNotification(requestDto.userId(),
+ "There is no free available car with id: "
+ + requestDto.carId());
+ throw new RuntimeException("There is no free available car with id: "
+ + requestDto.carId());
+ }
+ }
+
private String createOverdueRentalMessage(Rental rental) {
return "Overdue rental alert! Rental ID: " + rental.getId()
+ ", User ID: " + rental.getUser().getId()
diff --git a/src/main/java/service/carsharing/service/impl/UserServiceImpl.java b/src/main/java/service/carsharing/service/impl/UserServiceImpl.java
index 809e4fe..5c8fa7f 100644
--- a/src/main/java/service/carsharing/service/impl/UserServiceImpl.java
+++ b/src/main/java/service/carsharing/service/impl/UserServiceImpl.java
@@ -37,11 +37,8 @@ public UserResponseDto registration(UserRegistrationRequestDto requestDto) {
@Override
public UserWithRoleResponseDto updateRole(Long id, UserUpdateRoleRequestDto requestDto) {
- User user = userRepository.findByIdAndDeletedFalse(id)
- .orElseThrow(() -> new EntityNotFoundException("Can't find user with id: " + id));
- Role.RoleName roleName = Role.RoleName.valueOf(requestDto.role());
- Role role = roleRepository.findByName(roleName).orElseThrow(
- () -> new EntityNotFoundException("Can't find role with name=" + roleName));
+ User user = getUserById(id);
+ Role role = getRoleByRoleName(requestDto.role());
user.getRoles().add(role);
return userMapper.toDtoWithRole(userRepository.save(user));
}
@@ -63,4 +60,15 @@ private User getUserByEmail(String email) {
return userRepository.findByEmail(email).orElseThrow(
() -> new EntityNotFoundException("Can't find user with email: " + email));
}
+
+ private User getUserById(Long id) {
+ return userRepository.findByIdAndDeletedFalse(id)
+ .orElseThrow(() -> new EntityNotFoundException("Can't find user with id: " + id));
+ }
+
+ private Role getRoleByRoleName(String role) {
+ Role.RoleName roleName = Role.RoleName.valueOf(role);
+ return roleRepository.findByName(roleName).orElseThrow(
+ () -> new EntityNotFoundException("Can't find role with name=" + roleName));
+ }
}
diff --git a/src/test/java/service/carsharing/CarSharingApplicationTests.java b/src/test/java/service/carsharing/CarSharingApplicationTests.java
index eb3a873..ae976df 100644
--- a/src/test/java/service/carsharing/CarSharingApplicationTests.java
+++ b/src/test/java/service/carsharing/CarSharingApplicationTests.java
@@ -1,11 +1,7 @@
package service.carsharing;
-import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;
@SpringBootTest
class CarSharingApplicationTests {
- @Test
- void contextLoads(){
- }
}
diff --git a/src/test/java/service/carsharing/controller/CarControllerTest.java b/src/test/java/service/carsharing/controller/CarControllerTest.java
deleted file mode 100644
index c3cff95..0000000
--- a/src/test/java/service/carsharing/controller/CarControllerTest.java
+++ /dev/null
@@ -1,258 +0,0 @@
-package service.carsharing.controller;
-
-import static org.junit.jupiter.api.Assertions.assertEquals;
-import static org.junit.jupiter.api.Assertions.assertNotNull;
-import static org.springframework.security.test.web.servlet.setup.SecurityMockMvcConfigurers.springSecurity;
-import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
-import static org.testcontainers.shaded.org.apache.commons.lang3.builder.EqualsBuilder.reflectionEquals;
-
-import com.fasterxml.jackson.databind.ObjectMapper;
-import java.math.BigDecimal;
-import java.sql.Connection;
-import java.sql.SQLException;
-import java.util.Arrays;
-import java.util.List;
-import javax.sql.DataSource;
-import org.junit.jupiter.api.AfterAll;
-import org.junit.jupiter.api.BeforeAll;
-import org.junit.jupiter.api.DisplayName;
-import org.junit.jupiter.api.Test;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.context.SpringBootTest;
-import org.springframework.core.io.ClassPathResource;
-import org.springframework.http.MediaType;
-import org.springframework.jdbc.datasource.init.ScriptUtils;
-import org.springframework.security.test.context.support.WithMockUser;
-import org.springframework.test.context.jdbc.Sql;
-import org.springframework.test.web.servlet.MockMvc;
-import org.springframework.test.web.servlet.MvcResult;
-import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
-import org.springframework.test.web.servlet.setup.MockMvcBuilders;
-import org.springframework.web.context.WebApplicationContext;
-import service.carsharing.dto.cars.CarRequestDto;
-import service.carsharing.dto.cars.CarResponseDto;
-import service.carsharing.model.Car;
-
-@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
-public class CarControllerTest {
- private static final Long VALID_ID = 1L;
- private static final String VALID_MODEL = "Valid Model";
- private static final String VALID_BRAND = "Valid Brand";
- private static final Car.Type VALID_TYPE = Car.Type.CUV;
- private static final String VALID_STRING_TYPE = "SUV";
- private static final Integer VALID_INVENTORY = 2;
- private static final BigDecimal VALID_FEE = BigDecimal.TEN;
- private static final boolean NOT_DELETED = false;
-
- private static MockMvc mockMvc;
- @Autowired
- private ObjectMapper objectMapper;
-
- @BeforeAll
- static void beforeAll(
- @Autowired DataSource dataSource,
- @Autowired WebApplicationContext applicationContext
- ) throws SQLException {
- mockMvc = MockMvcBuilders
- .webAppContextSetup(applicationContext)
- .apply(springSecurity())
- .build();
- teardown(dataSource);
- try (Connection connection = dataSource.getConnection()) {
- connection.setAutoCommit(true);
- ScriptUtils.executeSqlScript(
- connection, new ClassPathResource("database/cars/add-two-cars.sql")
- );
- }
- }
-
- @AfterAll
- static void afterAll(@Autowired DataSource dataSource) throws SQLException {
- teardown(dataSource);
- }
-
- static void teardown(DataSource dataSource) throws SQLException {
- try (Connection connection = dataSource.getConnection()) {
- connection.setAutoCommit(true);
- ScriptUtils.executeSqlScript(
- connection, new ClassPathResource("database/cars/delete-all-from-cars.sql")
- );
- }
- }
-
- private Car createValidCar() {
- Car car = new Car();
- car.setId(VALID_ID);
- car.setInventory(VALID_INVENTORY);
- car.setFee(VALID_FEE);
- car.setDeleted(NOT_DELETED);
- car.setModel(VALID_MODEL);
- car.setBrand(VALID_BRAND);
- car.setType(VALID_TYPE);
- return car;
- }
-
- private CarRequestDto createValidCarRequestDto() {
- return new CarRequestDto(
- VALID_MODEL,
- VALID_BRAND,
- VALID_STRING_TYPE,
- VALID_INVENTORY,
- VALID_FEE
- );
- }
-
- private CarResponseDto createValidCarResponseDto() {
- return new CarResponseDto(
- VALID_ID,
- VALID_MODEL,
- VALID_BRAND,
- VALID_STRING_TYPE,
- VALID_INVENTORY,
- VALID_FEE
- );
- }
-
- @WithMockUser(username = "manager", roles = "MANAGER")
- @Test
- @Sql(
- scripts = "classpath:database/cars/delete-default-car.sql",
- executionPhase = Sql.ExecutionPhase.AFTER_TEST_METHOD
- )
- @DisplayName("Verify createCar() method work")
- public void createCar_ValidRequestDto_ReturnCarResponseDto() throws Exception {
- CarRequestDto requestDto = createValidCarRequestDto();
- CarResponseDto expected = createValidCarResponseDto();
-
- String jsonRequest = objectMapper.writeValueAsString(requestDto);
-
- MvcResult result = mockMvc.perform(MockMvcRequestBuilders.post("/api/cars")
- .content(jsonRequest)
- .contentType(MediaType.APPLICATION_JSON)
- )
- .andExpect(status().isCreated())
- .andReturn();
-
- CarResponseDto actual = objectMapper
- .readValue(result.getResponse().getContentAsString(), CarResponseDto.class);
-
- assertNotNull(actual);
- assertNotNull(actual.id());
- reflectionEquals(expected, actual, "id");
- }
-
- @WithMockUser(username = "customer", roles = "CUSTOMER")
- @Test
- @DisplayName("Verify getAllCars() method work")
- public void getAllCars_ValidCarInDb_ReturnAllCarsInDb() throws Exception {
- CarResponseDto firstCar = new CarResponseDto(
- 1L,
- "First model",
- "Audi",
- "SEDAN",
- 2,
- BigDecimal.valueOf(149.99)
- );
- CarResponseDto secondCar = new CarResponseDto(
- 2L,
- "Second model",
- "Nissan",
- "SUV",
- 3,
- BigDecimal.valueOf(99.99)
- );
- List expected = List.of(firstCar, secondCar);
-
- MvcResult result = mockMvc.perform(MockMvcRequestBuilders.get("/api/cars")
- .contentType(MediaType.APPLICATION_JSON))
- .andExpect(status().isOk())
- .andReturn();
- CarResponseDto[] actual = objectMapper
- .readValue(result.getResponse().getContentAsByteArray(), CarResponseDto[].class);
- assertEquals(2, actual.length);
- assertEquals(expected, Arrays.stream(actual).toList());
- }
-
- @WithMockUser(username = "customer", roles = "CUSTOMER")
- @Test
- @DisplayName("Verify getCarById() method work")
- public void getCarById_ValidId_CarResponseDto() throws Exception {
- CarResponseDto expected = new CarResponseDto(
- 1L,
- "First model",
- "Audi",
- "SEDAN",
- 2,
- BigDecimal.valueOf(149.99)
- );
- MvcResult result = mockMvc.perform(MockMvcRequestBuilders.get("/api/cars/{id}", 1L)
- .contentType(MediaType.APPLICATION_JSON))
- .andExpect(status().isOk())
- .andReturn();
-
- CarResponseDto actual = objectMapper
- .readValue(result.getResponse().getContentAsString(), CarResponseDto.class);
- assertNotNull(actual);
- reflectionEquals(expected, actual);
- }
-
- @WithMockUser(username = "manager", roles = {"MANAGER"})
- @Test
- @Sql(
- scripts = "classpath:database/cars/add-default-car.sql",
- executionPhase = Sql.ExecutionPhase.BEFORE_TEST_METHOD
- )
- @Sql(
- scripts = "classpath:database/cars/delete-default-car.sql",
- executionPhase = Sql.ExecutionPhase.AFTER_TEST_METHOD
- )
- @DisplayName("Verify deleteCar() method works")
- public void deleteCar_ValidId_ReturnNoContentStatus() throws Exception {
-
- mockMvc.perform(MockMvcRequestBuilders.delete("/api/cars/", 3L)
- .contentType(MediaType.APPLICATION_JSON))
- .andExpect(status().isNoContent());
- }
-
- @WithMockUser(username = "manager", roles = {"MANAGER"})
- @Test
- @Sql(
- scripts = "classpath:database/cars/add-default-car.sql",
- executionPhase = Sql.ExecutionPhase.BEFORE_TEST_METHOD
- )
- @Sql(
- scripts = "classpath:database/cars/delete-default-car.sql",
- executionPhase = Sql.ExecutionPhase.AFTER_TEST_METHOD
- )
- @DisplayName("Verify updateCar() method works")
- public void updateCar_ValidIdAndRequestDto_UpdatedCarInDb() throws Exception {
- CarRequestDto requestDto = new CarRequestDto(
- "new model",
- "new brand",
- VALID_STRING_TYPE,
- 1,
- VALID_FEE
- );
- CarResponseDto expected = new CarResponseDto(
- 3L,
- "new model",
- "new brand",
- VALID_STRING_TYPE,
- 1,
- VALID_FEE
- );
- String jsonRequest = objectMapper.writeValueAsString(requestDto);
-
- MvcResult result = mockMvc.perform(MockMvcRequestBuilders.put("api/cars/{id}", 3L)
- .content(jsonRequest)
- .contentType(MediaType.APPLICATION_JSON))
- .andExpect(status().isOk())
- .andReturn();
-
- CarResponseDto actual = objectMapper
- .readValue(result.getResponse().getContentAsString(), CarResponseDto.class);
- assertNotNull(actual);
- reflectionEquals(expected, actual);
-
- }
-}
diff --git a/src/test/java/service/carsharing/repository/CarRepositoryTest.java b/src/test/java/service/carsharing/repository/CarRepositoryTest.java
deleted file mode 100644
index 3a50339..0000000
--- a/src/test/java/service/carsharing/repository/CarRepositoryTest.java
+++ /dev/null
@@ -1,54 +0,0 @@
-package service.carsharing.repository;
-
-import java.math.BigDecimal;
-import org.junit.jupiter.api.Assertions;
-import org.junit.jupiter.api.Test;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
-import org.springframework.test.context.jdbc.Sql;
-import service.carsharing.model.Car;
-
-@DataJpaTest
-@Sql(
- scripts = "classpath:database/cars/add-default-car.sql",
- executionPhase = Sql.ExecutionPhase.BEFORE_TEST_METHOD
-)
-@Sql(
- scripts = "classpath:database/cars/delete-default-car.sql",
- executionPhase = Sql.ExecutionPhase.AFTER_TEST_METHOD
-)
-@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
-public class CarRepositoryTest {
- private static final Long VALID_ID = 3L;
- private static final String VALID_MODEL = "Valid Model";
- private static final String VALID_BRAND = "Valid Brand";
- private static final Car.Type VALID_TYPE = Car.Type.CUV;
- private static final Integer VALID_INVENTORY = 2;
- private static final BigDecimal VALID_FEE = BigDecimal.TEN;
- private static final boolean NOT_DELETED = false;
- @Autowired
- private CarRepository carRepository;
-
- private Car createValidCar() {
- Car car = new Car();
- car.setId(VALID_ID);
- car.setInventory(VALID_INVENTORY);
- car.setFee(VALID_FEE);
- car.setDeleted(NOT_DELETED);
- car.setModel(VALID_MODEL);
- car.setBrand(VALID_BRAND);
- car.setType(VALID_TYPE);
- return car;
- }
-
- @Test
- public void findCarById_ValidId_ValidCar() {
- Car expected = createValidCar();
- Car actual = carRepository.findById(VALID_ID).get();
-
- Assertions.assertNotNull(actual);
- Assertions.assertEquals(expected, actual);
-
- }
-}
diff --git a/src/test/java/service/carsharing/service/CarServiceTest.java b/src/test/java/service/carsharing/service/CarServiceTest.java
index 36572a2..98396c5 100644
--- a/src/test/java/service/carsharing/service/CarServiceTest.java
+++ b/src/test/java/service/carsharing/service/CarServiceTest.java
@@ -133,19 +133,23 @@ public void getCar_NotValidID_EntityNotFoundException() {
}
@Test
+ @DisplayName("Verify updateCar() method works")
public void updateCar_ValidIdAndRequestDto_UpdaterCar() {
+ // Arrange
Car car = createValidCar();
CarRequestDto requestDto = createValidCarRequestDto();
CarResponseDto expected = createValidCarResponseDto();
- when(carRepository.findByIdAndDeletedFalse(VALID_ID))
- .thenReturn(Optional.of(car));
- when(carMapper.toModel(requestDto)).thenReturn(car);
+ when(carRepository.findByIdAndDeletedFalse(VALID_ID)).thenReturn(Optional.of(car));
when(carRepository.save(car)).thenReturn(car);
when(carMapper.toDto(car)).thenReturn(expected);
+ // Act
CarResponseDto actual = carService.updateCar(VALID_ID, requestDto);
+ // Assert
assertEquals(expected, actual);
+ verify(carMapper).updateCar(requestDto, car);
+ verify(carRepository).save(car);
}
@Test