Merge pull request 'develop' (#3) from develop into master
Reviewed-on: #3
Before Width: | Height: | Size: 6.9 KiB |
Before Width: | Height: | Size: 10 KiB |
Before Width: | Height: | Size: 8.7 KiB |
Before Width: | Height: | Size: 7.9 KiB |
Before Width: | Height: | Size: 10 KiB |
Before Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 9.2 KiB |
Before Width: | Height: | Size: 12 KiB |
Before Width: | Height: | Size: 8.9 KiB |
Before Width: | Height: | Size: 9.1 KiB |
Before Width: | Height: | Size: 7.9 KiB |
Before Width: | Height: | Size: 7.8 KiB |
Before Width: | Height: | Size: 8.9 KiB |
Before Width: | Height: | Size: 8.5 KiB |
Before Width: | Height: | Size: 9.0 KiB |
Before Width: | Height: | Size: 8.7 KiB |
Before Width: | Height: | Size: 9.0 KiB |
Before Width: | Height: | Size: 8.6 KiB |
Before Width: | Height: | Size: 8.4 KiB |
Before Width: | Height: | Size: 6.8 KiB |
Before Width: | Height: | Size: 9.7 KiB |
Before Width: | Height: | Size: 11 KiB |
Before Width: | Height: | Size: 10 KiB |
Before Width: | Height: | Size: 9.5 KiB |
Before Width: | Height: | Size: 8.7 KiB |
Before Width: | Height: | Size: 8.8 KiB |
@ -25,7 +25,7 @@ public class Passage {
|
||||
@Column(name = "passage", unique = true)
|
||||
@NotBlank(message = "Название не может быть пустым!")
|
||||
@Size(max = 100, message = "Максимальная длина названия 100 символов!")
|
||||
private String passage;
|
||||
private String passageName;
|
||||
|
||||
@OneToMany(mappedBy = "passage")
|
||||
private List<Visit> visits;
|
||||
|
@ -31,6 +31,7 @@ public class Terminal {
|
||||
// Мне нужна была рандомная генерация кода для терминала, так что я мог сделать кривую реализацию через самописную функцию,
|
||||
// но боялся, что она будет генерировать не уникальные значения. (я очень смутно представляю, как эта штука работает)
|
||||
// Код взят отсюда: https://stackoverflow.com/questions/25082244/auto-generate-unique-random-string-in-spring-mvc-hibernate
|
||||
// todo: Понять что это такое.......................................................................................
|
||||
@GenericGenerator(name = "uuid-gen", strategy = "uuid")
|
||||
@GeneratedValue(generator = "uuid-gen")
|
||||
@NotBlank(message = "Код не может быть пустым!")
|
||||
|
@ -30,7 +30,7 @@ public class Visit {
|
||||
private LocalDateTime endVisit;
|
||||
|
||||
@Column(name = "is_finished", nullable = false)
|
||||
private final boolean isFinished = false;
|
||||
private boolean isFinished = false;
|
||||
|
||||
@ManyToOne(fetch = FetchType.EAGER)
|
||||
@JoinColumn(name = "start_terminal_id", referencedColumnName = "code", nullable = false)
|
||||
|
@ -0,0 +1,8 @@
|
||||
package com.example.nto.domain.exception;
|
||||
|
||||
public class AccessDeniedException extends RuntimeException {
|
||||
public AccessDeniedException(String message) {
|
||||
// Доступ запрещен.
|
||||
super();
|
||||
}
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
package com.example.nto.domain.exception;
|
||||
|
||||
public class ConflictResourceException extends RuntimeException {
|
||||
public ConflictResourceException(String message) {
|
||||
// Вызывается, когда данные в таблицах конфликтуют.
|
||||
super(message);
|
||||
}
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
package com.example.nto.domain.exception;
|
||||
|
||||
public class ImageSendException extends RuntimeException {
|
||||
public ImageSendException(String message) {
|
||||
// Вызывается при ошибке во время отправки изображения.
|
||||
super(message);
|
||||
}
|
||||
}
|
@ -0,0 +1,7 @@
|
||||
package com.example.nto.domain.exception;
|
||||
|
||||
public class ImageUploadException extends RuntimeException {
|
||||
public ImageUploadException(String message) {
|
||||
super(message);
|
||||
}
|
||||
}
|
@ -0,0 +1,8 @@
|
||||
package com.example.nto.domain.exception;
|
||||
|
||||
public class ResourceNotFoundException extends RuntimeException {
|
||||
public ResourceNotFoundException(String message) {
|
||||
// Вызывается, когда что-то не найдено в бд.
|
||||
super(message);
|
||||
}
|
||||
}
|
@ -0,0 +1,36 @@
|
||||
package com.example.nto.domain.exception.advice;
|
||||
|
||||
import com.amazonaws.SdkBaseException;
|
||||
import com.amazonaws.SdkClientException;
|
||||
import com.amazonaws.services.s3.model.AmazonS3Exception;
|
||||
import com.example.nto.domain.exception.model.ApiError;
|
||||
import com.example.nto.utils.Utils;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.ControllerAdvice;
|
||||
import org.springframework.web.bind.annotation.ExceptionHandler;
|
||||
|
||||
import java.util.concurrent.ExecutionException;
|
||||
|
||||
import static com.example.nto.utils.DataFormatType.DATE_TIME;
|
||||
|
||||
@Slf4j
|
||||
@ControllerAdvice
|
||||
public class ExceptionApiHandler {
|
||||
@ExceptionHandler({AmazonS3Exception.class, SdkClientException.class})
|
||||
public ResponseEntity<ApiError> amazonS3Exception(SdkBaseException e) {
|
||||
return new ResponseEntity<>(
|
||||
new ApiError("500", "Что-то пошло не так с AWS SDK.", e.getMessage(), Utils.nowTime(DATE_TIME)),
|
||||
HttpStatus.INTERNAL_SERVER_ERROR
|
||||
);
|
||||
}
|
||||
|
||||
@ExceptionHandler({InterruptedException.class, ExecutionException.class})
|
||||
public ResponseEntity<ApiError> runtimeException(RuntimeException e) {
|
||||
return new ResponseEntity<>(
|
||||
new ApiError("500", "Один из потоков завершился исключением.", e.getMessage(), Utils.nowTime(DATE_TIME)),
|
||||
HttpStatus.INTERNAL_SERVER_ERROR
|
||||
);
|
||||
}
|
||||
}
|
@ -1,8 +1,7 @@
|
||||
package com.example.nto.domain.exception.advice;
|
||||
|
||||
import com.example.nto.domain.exception.CodeNotFoundException;
|
||||
import com.example.nto.domain.exception.EmployeeNotFoundException;
|
||||
import com.example.nto.domain.exception.SomethingWentWrongException;
|
||||
import com.amazonaws.services.organizations.model.ConstraintViolationException;
|
||||
import com.example.nto.domain.exception.*;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.ControllerAdvice;
|
||||
@ -27,4 +26,36 @@ public class GlobalExceptionalHandler {
|
||||
public ResponseEntity<HttpStatus> handlerSomethingWentWrongException(SomethingWentWrongException e) {
|
||||
return new ResponseEntity<>(HttpStatus.BAD_REQUEST);
|
||||
}
|
||||
|
||||
@ExceptionHandler(AccessDeniedException.class)
|
||||
public ResponseEntity<String> handlerAccessDeniedException(AccessDeniedException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.UNAUTHORIZED);
|
||||
}
|
||||
|
||||
@ExceptionHandler(ResourceNotFoundException.class)
|
||||
public ResponseEntity<String> handlerAccessDeniedException(ResourceNotFoundException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.NOT_FOUND);
|
||||
}
|
||||
|
||||
@ExceptionHandler(ConflictResourceException.class)
|
||||
public ResponseEntity<String> handlerConflictResourceException(ConflictResourceException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.CONFLICT);
|
||||
}
|
||||
|
||||
@ExceptionHandler(ImageUploadException.class)
|
||||
public ResponseEntity<String> handlerImageUploadException(ImageUploadException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.INTERNAL_SERVER_ERROR);
|
||||
}
|
||||
|
||||
@ExceptionHandler(ImageSendException.class)
|
||||
public ResponseEntity<String> handlerImageSendException(ImageSendException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.INTERNAL_SERVER_ERROR);
|
||||
}
|
||||
|
||||
@ExceptionHandler(ConstraintViolationException.class)
|
||||
public ResponseEntity<String> handlerConstraintViolationException(ConstraintViolationException e) {
|
||||
return new ResponseEntity<>(e.getMessage(), HttpStatus.BAD_REQUEST);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -0,0 +1,14 @@
|
||||
package com.example.nto.domain.exception.model;
|
||||
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@AllArgsConstructor
|
||||
public class ApiError {
|
||||
private String status; // Код статуса HTTP-ответа
|
||||
private String reason; // Общее описание причины ошибки
|
||||
private String message; // Сообщение об ошибке
|
||||
private String timestamp; // Дата и время когда произошла ошибка (в формате "yyyy-MM-dd HH:mm:ss")
|
||||
}
|
@ -24,4 +24,6 @@ public class VisitDTO {
|
||||
// превратить обратно можно с помощью LocalDateTime.parse().
|
||||
private String durationVisit;
|
||||
private String officeName;
|
||||
|
||||
private String typePassage; // Строка либо PASSAGE_CARD, либо PASSAGE_TELEPHONE
|
||||
}
|
||||
|
@ -16,6 +16,7 @@ public class EmployeeDTO {
|
||||
private String name;
|
||||
private String surname;
|
||||
private String patronymic;
|
||||
private String aboutMe;
|
||||
private String telephone;
|
||||
private String email;
|
||||
|
||||
@ -23,7 +24,7 @@ public class EmployeeDTO {
|
||||
private String officeName;
|
||||
private String officeImageUrl;
|
||||
|
||||
private String position; // Название должности
|
||||
private String positionName; // Название должности
|
||||
private String role; // строка либо ROLE_USER, либо ROLE_ADMIN
|
||||
|
||||
private String profileImageUrl;
|
||||
|
@ -1,4 +1,48 @@
|
||||
package com.example.nto.dto.mappers;
|
||||
|
||||
import com.example.nto.domain.entity.Office;
|
||||
import com.example.nto.dto.entity.OfficeDTO;
|
||||
import com.example.nto.dto.mappers.employee.EmployeeItemMapper;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@UtilityClass
|
||||
public class OfficeMapper {
|
||||
public static OfficeDTO convertToDTO(Office office) {
|
||||
OfficeDTO officeDTO = new OfficeDTO();
|
||||
|
||||
officeDTO.setId(office.getId());
|
||||
officeDTO.setName(office.getName());
|
||||
officeDTO.setDescription(office.getDescription());
|
||||
officeDTO.setAddress(office.getAddress());
|
||||
officeDTO.setLatitude(office.getLatitude());
|
||||
officeDTO.setLongitude(office.getLongitude());
|
||||
officeDTO.setLinkLogo(office.getLinkLogo());
|
||||
officeDTO.setTelephone(office.getTelephone());
|
||||
officeDTO.setEmail(office.getEmail());
|
||||
|
||||
officeDTO.setEmployees(office.getEmployeeList().stream().map(EmployeeItemMapper::convertToDTO).collect(Collectors.toList()));
|
||||
officeDTO.setTerminals(office.getTerminals().stream().map(TerminalMapper::convertToDTO).collect(Collectors.toList()));
|
||||
|
||||
return officeDTO;
|
||||
}
|
||||
|
||||
public static Office convertFromDTO(OfficeDTO officeDTO) {
|
||||
Office office = new Office();
|
||||
|
||||
office.setId(officeDTO.getId());
|
||||
office.setName(officeDTO.getName());
|
||||
office.setDescription(officeDTO.getDescription());
|
||||
office.setAddress(officeDTO.getAddress());
|
||||
office.setLatitude(officeDTO.getLatitude());
|
||||
office.setLongitude(officeDTO.getLongitude());
|
||||
office.setLinkLogo(officeDTO.getLinkLogo());
|
||||
office.setTelephone(officeDTO.getTelephone());
|
||||
office.setEmail(officeDTO.getEmail());
|
||||
|
||||
// todo: Проверить, возможно, здесь нужно office.setEmployeeList() и office.setTerminals()
|
||||
|
||||
return office;
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,21 @@
|
||||
package com.example.nto.dto.mappers;
|
||||
|
||||
import com.example.nto.domain.entity.Position;
|
||||
import com.example.nto.dto.entity.PositionDTO;
|
||||
import com.example.nto.dto.mappers.employee.EmployeeItemMapper;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@UtilityClass
|
||||
public class PositionMapper {
|
||||
}
|
||||
public static PositionDTO convertToDTO(Position position) {
|
||||
PositionDTO positionDTO = new PositionDTO();
|
||||
|
||||
positionDTO.setId(position.getId());
|
||||
positionDTO.setName(position.getName());
|
||||
positionDTO.setEmployeeItemDTOList(position.getEmployees().stream().map(EmployeeItemMapper::convertToDTO).collect(Collectors.toList()));
|
||||
|
||||
return positionDTO;
|
||||
}
|
||||
}
|
@ -1,4 +1,29 @@
|
||||
package com.example.nto.dto.mappers;
|
||||
|
||||
import com.example.nto.domain.entity.Office;
|
||||
import com.example.nto.domain.entity.Terminal;
|
||||
import com.example.nto.dto.entity.TerminalDTO;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
@UtilityClass
|
||||
public class TerminalMapper {
|
||||
public static TerminalDTO convertToDTO(Terminal terminal) {
|
||||
TerminalDTO terminalDTO = new TerminalDTO();
|
||||
|
||||
terminalDTO.setId(terminal.getId());
|
||||
terminalDTO.setName(terminal.getName());
|
||||
terminalDTO.setCode(terminal.getCode());
|
||||
terminalDTO.setOfficeName(terminal.getOffice().getName());
|
||||
|
||||
return terminalDTO;
|
||||
}
|
||||
|
||||
public static Terminal convertFromDTO(TerminalDTO terminalDTO, Office office) {
|
||||
Terminal terminal = new Terminal();
|
||||
|
||||
terminal.setName(terminalDTO.getName());
|
||||
terminal.setOffice(office);
|
||||
|
||||
return terminal;
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,42 @@
|
||||
package com.example.nto.dto.mappers;
|
||||
|
||||
|
||||
import com.example.nto.domain.entity.Employee;
|
||||
import com.example.nto.domain.entity.Passage;
|
||||
import com.example.nto.domain.entity.Terminal;
|
||||
import com.example.nto.domain.entity.Visit;
|
||||
import com.example.nto.dto.entity.VisitDTO;
|
||||
import com.example.nto.utils.Utils;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
|
||||
@UtilityClass
|
||||
public class VisitMapper {
|
||||
public static VisitDTO convertToDTO(Visit visit) {
|
||||
VisitDTO visitDTO = new VisitDTO();
|
||||
|
||||
visitDTO.setId(visit.getId());
|
||||
visitDTO.setStartVisit(visit.getStartVisit().toString());
|
||||
visitDTO.setEndVisit(visit.getEndVisit().toString());
|
||||
visitDTO.setFinished(visit.isFinished());
|
||||
visitDTO.setDurationVisit(Utils.period(visit.getStartVisit(), visit.getEndVisit()).toString());
|
||||
visitDTO.setOfficeName(visit.getStartTerminal().getOffice().getName());
|
||||
visitDTO.setTypePassage(visit.getPassage().getPassageName());
|
||||
|
||||
return visitDTO;
|
||||
}
|
||||
|
||||
public static Visit convertFromDTO(Terminal terminal, Employee employee, Passage passage) {
|
||||
Visit visit = new Visit();
|
||||
|
||||
visit.setEmployee(employee);
|
||||
visit.setStartVisit(LocalDateTime.now());
|
||||
visit.setFinished(false);
|
||||
visit.setStartTerminal(terminal);
|
||||
visit.setPassage(passage);
|
||||
|
||||
return visit;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -26,6 +26,7 @@ public class EmployeeCreateMapper {
|
||||
employee.setPosition(position);
|
||||
employee.setRole(role);
|
||||
employee.setProfileImageUrl(Utils.getRandomUrlProfileImage());
|
||||
employee.setBlocked(false);
|
||||
|
||||
return employee;
|
||||
}
|
||||
|
@ -1,4 +1,31 @@
|
||||
package com.example.nto.dto.mappers.employee;
|
||||
|
||||
import com.example.nto.domain.entity.Employee;
|
||||
import com.example.nto.domain.entity.Visit;
|
||||
import com.example.nto.dto.entity.employee.EmployeeItemDTO;
|
||||
import com.example.nto.utils.Utils;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@UtilityClass
|
||||
public class EmployeeItemMapper {
|
||||
public static EmployeeItemDTO convertToDTO(Employee employee) {
|
||||
EmployeeItemDTO employeeItemDTO = new EmployeeItemDTO();
|
||||
employeeItemDTO.setId(employee.getId());
|
||||
employeeItemDTO.setName(employee.getName());
|
||||
employeeItemDTO.setSurname(employee.getSurname());
|
||||
employeeItemDTO.setPatronymic(employee.getPatronymic());
|
||||
employeeItemDTO.setProfileImageUrl(employee.getProfileImageUrl());
|
||||
employeeItemDTO.setOfficeName(employee.getOffice().getName());
|
||||
employeeItemDTO.setPosition(employee.getPosition().getName());
|
||||
employeeItemDTO.setBlocked(employee.isBlocked());
|
||||
|
||||
// todo: Протестировать работу!
|
||||
|
||||
List<Visit> visitsLast30Days = Utils.filterDateLast30Days(employee.getVisits());
|
||||
employeeItemDTO.setVisitStatus(visitsLast30Days.stream().anyMatch(visit -> !visit.isFinished()));
|
||||
|
||||
return employeeItemDTO;
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,81 @@
|
||||
package com.example.nto.dto.mappers.employee;
|
||||
|
||||
import com.example.nto.domain.entity.*;
|
||||
import com.example.nto.dto.entity.employee.EmployeeDTO;
|
||||
import com.example.nto.utils.Utils;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
@UtilityClass
|
||||
public class EmployeeMapper {
|
||||
public static EmployeeDTO convertToDTO(Employee employee) {
|
||||
EmployeeDTO employeeDTO = new EmployeeDTO();
|
||||
|
||||
employeeDTO.setId(employee.getId());
|
||||
employeeDTO.setName(employee.getName());
|
||||
employeeDTO.setSurname(employee.getSurname());
|
||||
employeeDTO.setPatronymic(employee.getPatronymic());
|
||||
employeeDTO.setAboutMe(employeeDTO.getAboutMe());
|
||||
employeeDTO.setTelephone(employee.getTelephone());
|
||||
employeeDTO.setEmail(employee.getEmail());
|
||||
|
||||
employeeDTO.setOfficeId(employee.getOffice().getId());
|
||||
employeeDTO.setOfficeName(employee.getOffice().getName());
|
||||
employeeDTO.setOfficeImageUrl(employee.getOffice().getLinkLogo());
|
||||
employeeDTO.setPositionName(employee.getPosition().getName());
|
||||
employeeDTO.setRole(employee.getRole().getRoleName());
|
||||
employeeDTO.setRole(employee.getProfileImageUrl());
|
||||
employeeDTO.setBlocked(employee.isBlocked());
|
||||
|
||||
List<Visit> visitsLast30Days = Utils.filterDateLast30Days(employee.getVisits());
|
||||
|
||||
boolean visitStatus = false;
|
||||
String startVisitDateTime = null;
|
||||
String currentOfficeName = null;
|
||||
List<Long> visitsIdLast30Days = new ArrayList<>(visitsLast30Days.size());
|
||||
List<List<LocalDateTime>> periods = new ArrayList<>(visitsLast30Days.size());
|
||||
|
||||
for (Visit visit : visitsLast30Days) {
|
||||
if (!visit.isFinished()) {
|
||||
if (visitStatus) throw new IllegalStateException("У работника два посещения одновременно!");
|
||||
|
||||
visitStatus = true;
|
||||
startVisitDateTime = visit.getStartVisit().toString();
|
||||
currentOfficeName = visit.getStartTerminal().getOffice().getName();
|
||||
}
|
||||
visitsIdLast30Days.add(visit.getId());
|
||||
periods.add(List.of(visit.getStartVisit(), visit.getEndVisit()));
|
||||
}
|
||||
|
||||
employeeDTO.setVisitStatus(visitStatus);
|
||||
employeeDTO.setStartVisitDateTime(startVisitDateTime);
|
||||
employeeDTO.setCurrentOfficeName(currentOfficeName);
|
||||
employeeDTO.setVisitsIdLast30Days(visitsIdLast30Days);
|
||||
employeeDTO.setTotalTimeVisitsLast30Days(Utils.periods(periods));
|
||||
employeeDTO.setCreateAt(employee.getCreatedAt().toString());
|
||||
|
||||
return employeeDTO;
|
||||
}
|
||||
|
||||
public static Employee convertFromDTO(EmployeeDTO employeeDTO, Office office, Position position, Role role) {
|
||||
Employee employee = new Employee();
|
||||
|
||||
employee.setName(employeeDTO.getName());
|
||||
employee.setSurname(employeeDTO.getSurname());
|
||||
employee.setPatronymic(employeeDTO.getPatronymic());
|
||||
employeeDTO.setAboutMe(employee.getAboutMe());
|
||||
employee.setTelephone(employeeDTO.getTelephone());
|
||||
employee.setEmail(employeeDTO.getEmail());
|
||||
employee.setOffice(office);
|
||||
employee.setPosition(position);
|
||||
employee.setRole(role);
|
||||
employee.setProfileImageUrl(employeeDTO.getProfileImageUrl());
|
||||
employee.setBlocked(employeeDTO.isBlocked());
|
||||
|
||||
return employee;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -0,0 +1,11 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Employee;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface EmployeeRepository extends JpaRepository<Employee, Long> {
|
||||
Optional<Employee> findByEmail(String email);
|
||||
Optional<Employee> findByTelephone(String telephone);
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Office;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface OfficeRepository extends JpaRepository<Office, Long> {
|
||||
Optional<Office> findByName(String name);
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Passage;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface PassageRepository extends JpaRepository<Passage, Long> {
|
||||
Optional<Passage> findByPassageName(String passageName);
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Position;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface PositionRepository extends JpaRepository<Position, Long> {
|
||||
Optional<Position> findByName(String name);
|
||||
}
|
10
src/main/java/com/example/nto/repository/RoleRepository.java
Normal file
@ -0,0 +1,10 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Role;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface RoleRepository extends JpaRepository<Role, Long> {
|
||||
Optional<Role> findByRoleName(String roleName);
|
||||
}
|
@ -0,0 +1,10 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Terminal;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
public interface TerminalRepository extends JpaRepository<Terminal, Long> {
|
||||
Optional<Terminal> findByCode(String code);
|
||||
}
|
@ -0,0 +1,7 @@
|
||||
package com.example.nto.repository;
|
||||
|
||||
import com.example.nto.domain.entity.Visit;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
|
||||
public interface VisitRepository extends JpaRepository<Visit, Long> {
|
||||
}
|
23
src/main/java/com/example/nto/service/EmployeeService.java
Normal file
@ -0,0 +1,23 @@
|
||||
package com.example.nto.service;
|
||||
|
||||
import com.example.nto.dto.entity.employee.EmployeeCreateDTO;
|
||||
import com.example.nto.dto.entity.employee.EmployeeDTO;
|
||||
import com.example.nto.dto.entity.employee.EmployeeItemDTO;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public interface EmployeeService {
|
||||
List<EmployeeItemDTO> getAll();
|
||||
List<EmployeeItemDTO> getWorkingEmployee(boolean isWorking);
|
||||
|
||||
EmployeeDTO getById(long employeeId);
|
||||
EmployeeDTO getByEmail(String email);
|
||||
EmployeeDTO getByTelephone(String telephone);
|
||||
|
||||
EmployeeDTO create(EmployeeCreateDTO employeeCreateDTO);
|
||||
EmployeeDTO update(long employeeId, EmployeeDTO employeeDTO);
|
||||
void delete(long employeeId);
|
||||
|
||||
void patchProfileImage(long employeeId, String imageUrl);
|
||||
void patchBlockEmployee(long employeeId, boolean blockStatus);
|
||||
}
|
15
src/main/java/com/example/nto/service/OfficeService.java
Normal file
@ -0,0 +1,15 @@
|
||||
package com.example.nto.service;
|
||||
|
||||
import com.example.nto.dto.entity.OfficeDTO;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public interface OfficeService {
|
||||
List<OfficeDTO> getAllOffice();
|
||||
List<OfficeDTO> getAllSortedDistance(double userLatitude, double userLongitude);
|
||||
OfficeDTO getById(long officeId);
|
||||
|
||||
OfficeDTO create(OfficeDTO officeDTO);
|
||||
OfficeDTO update(long officeId, OfficeDTO officeDTO);
|
||||
void delete(long officeId);
|
||||
}
|
16
src/main/java/com/example/nto/service/TerminalService.java
Normal file
@ -0,0 +1,16 @@
|
||||
package com.example.nto.service;
|
||||
|
||||
import com.example.nto.dto.entity.TerminalDTO;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public interface TerminalService {
|
||||
List<TerminalDTO> getAllTerminal();
|
||||
TerminalDTO getById(long terminalId);
|
||||
|
||||
TerminalDTO create(TerminalDTO terminalDTO);
|
||||
TerminalDTO update(long terminalId, TerminalDTO terminalDTO);
|
||||
void delete(long terminalId);
|
||||
|
||||
TerminalDTO checkCode(String code);
|
||||
}
|
21
src/main/java/com/example/nto/service/VisitService.java
Normal file
@ -0,0 +1,21 @@
|
||||
package com.example.nto.service;
|
||||
|
||||
import com.example.nto.dto.entity.VisitDTO;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
|
||||
public interface VisitService {
|
||||
List<VisitDTO> getAll();
|
||||
List<VisitDTO> getAllVisitByEmployee(long employeeId);
|
||||
List<VisitDTO> getAllVisitByPeriod(LocalDateTime start, LocalDateTime stop);
|
||||
List<VisitDTO> getAllFinished(boolean isFinished);
|
||||
|
||||
VisitDTO getById(long visitId);
|
||||
VisitDTO open(long employeeId, long startTerminalId, String passageName);
|
||||
void exit(long employeeId, long endTerminalId);
|
||||
|
||||
// update не нужен он не будет использоваться :)
|
||||
|
||||
void delete(long visitId);
|
||||
}
|
@ -0,0 +1,156 @@
|
||||
package com.example.nto.service.impl;
|
||||
|
||||
import com.example.nto.aspect.annotation.LogExample;
|
||||
import com.example.nto.domain.entity.*;
|
||||
import com.example.nto.domain.exception.ConflictResourceException;
|
||||
import com.example.nto.domain.exception.ResourceNotFoundException;
|
||||
import com.example.nto.dto.entity.employee.EmployeeCreateDTO;
|
||||
import com.example.nto.dto.entity.employee.EmployeeDTO;
|
||||
import com.example.nto.dto.entity.employee.EmployeeItemDTO;
|
||||
import com.example.nto.dto.mappers.employee.EmployeeCreateMapper;
|
||||
import com.example.nto.dto.mappers.employee.EmployeeItemMapper;
|
||||
import com.example.nto.dto.mappers.employee.EmployeeMapper;
|
||||
import com.example.nto.repository.EmployeeRepository;
|
||||
import com.example.nto.repository.OfficeRepository;
|
||||
import com.example.nto.repository.PositionRepository;
|
||||
import com.example.nto.repository.RoleRepository;
|
||||
import com.example.nto.service.EmployeeService;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.security.crypto.password.PasswordEncoder;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class EmployeeServiceImpl implements EmployeeService {
|
||||
private final EmployeeRepository employeeRepository;
|
||||
private final OfficeRepository officeRepository;
|
||||
private final RoleRepository roleRepository;
|
||||
private final PositionRepository positionRepository;
|
||||
private final PasswordEncoder passwordEncoder;
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<EmployeeItemDTO> getAll() {
|
||||
return employeeRepository.findAll().stream().map(EmployeeItemMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<EmployeeItemDTO> getWorkingEmployee(boolean isWorking) {
|
||||
return employeeRepository.findAll().stream().filter(employee -> checkWorking(employee, isWorking))
|
||||
.map(EmployeeItemMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public EmployeeDTO getById(long employeeId) {
|
||||
return employeeRepository.findById(employeeId).map(EmployeeMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public EmployeeDTO getByEmail(String email) {
|
||||
return employeeRepository.findByEmail(email).map(EmployeeMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с email (" + email + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public EmployeeDTO getByTelephone(String telephone) {
|
||||
return employeeRepository.findByTelephone(telephone).map(EmployeeMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с telephone (" + telephone + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public EmployeeDTO create(EmployeeCreateDTO employeeCreateDTO) {
|
||||
Optional<Employee> employeeEmail = employeeRepository.findByEmail(employeeCreateDTO.getEmail());
|
||||
Optional<Employee> employeeTelephone = employeeRepository.findByTelephone(employeeCreateDTO.getTelephone());
|
||||
|
||||
if (employeeEmail.isPresent() || employeeTelephone.isPresent()) {
|
||||
throw new ConflictResourceException("Пользователь с таким email или телефоном уже существует!");
|
||||
}
|
||||
|
||||
Office office = officeRepository.findByName(employeeCreateDTO.getOfficeName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с именем (" + employeeCreateDTO.getOfficeName() + ") не найден!"));
|
||||
Position position = positionRepository.findByName(employeeCreateDTO.getPositionName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Позиция с именем (" + employeeCreateDTO.getPositionName() + ") не найден!"));
|
||||
Role role = roleRepository.findByRoleName(employeeCreateDTO.getRole())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Роль с названием (" + employeeCreateDTO.getRole() + ") не найден!"));
|
||||
|
||||
return EmployeeMapper.convertToDTO(employeeRepository.save(
|
||||
EmployeeCreateMapper.convertFromDTO(employeeCreateDTO, passwordEncoder.encode(employeeCreateDTO.getPassword()), office, position, role)));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public EmployeeDTO update(long employeeId, EmployeeDTO employeeDTO) {
|
||||
Employee employee = employeeRepository.findById(employeeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
|
||||
Optional<Employee> employeeEmail = employeeRepository.findByEmail(employeeDTO.getEmail());
|
||||
Optional<Employee> employeeTelephone = employeeRepository.findByTelephone(employeeDTO.getTelephone());
|
||||
|
||||
if (employeeEmail.isPresent() || employeeTelephone.isPresent()) {
|
||||
throw new ConflictResourceException("Пользователь с таким email или телефоном уже существует!");
|
||||
}
|
||||
|
||||
Office office = officeRepository.findByName(employeeDTO.getOfficeName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с именем (" + employeeDTO.getOfficeName() + ") не найден!"));
|
||||
Position position = positionRepository.findByName(employeeDTO.getPositionName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Позиция с именем (" + employeeDTO.getPositionName() + ") не найден!"));
|
||||
|
||||
employee.setName(employeeDTO.getName());
|
||||
employee.setSurname(employeeDTO.getSurname());
|
||||
employee.setPatronymic(employeeDTO.getPatronymic());
|
||||
employee.setAboutMe(employeeDTO.getAboutMe());
|
||||
employee.setTelephone(employee.getTelephone());
|
||||
employee.setEmail(employee.getEmail());
|
||||
employee.setOffice(office);
|
||||
employee.setPosition(position);
|
||||
|
||||
// profileImageUrl меняется в отдельном эндпоинте
|
||||
|
||||
employee.setBlocked(employeeDTO.isBlocked());
|
||||
|
||||
return EmployeeMapper.convertToDTO(employeeRepository.save(employee));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void delete(long employeeId) {
|
||||
employeeRepository.findById(employeeId).orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
employeeRepository.deleteById(employeeId);
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void patchProfileImage(long employeeId, String imageUrl) {
|
||||
Employee employee = employeeRepository.findById(employeeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
employee.setProfileImageUrl(imageUrl);
|
||||
employeeRepository.save(employee);
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void patchBlockEmployee(long employeeId, boolean blockStatus) {
|
||||
Employee employee = employeeRepository.findById(employeeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
employee.setBlocked(blockStatus);
|
||||
employeeRepository.save(employee);
|
||||
}
|
||||
|
||||
private static boolean checkWorking(Employee employee, boolean isWorking) {
|
||||
List<Visit> visits = employee.getVisits().stream().filter(visit -> !visit.isFinished()).collect(Collectors.toList());
|
||||
|
||||
if (visits.isEmpty()) return !isWorking;
|
||||
else if (visits.size() == 1) return isWorking;
|
||||
else throw new IllegalStateException("Пользователь не может находится в суперпозиции");
|
||||
}
|
||||
}
|
@ -0,0 +1,84 @@
|
||||
package com.example.nto.service.impl;
|
||||
|
||||
import com.example.nto.aspect.annotation.LogExample;
|
||||
import com.example.nto.domain.entity.Office;
|
||||
import com.example.nto.domain.exception.ResourceNotFoundException;
|
||||
import com.example.nto.dto.entity.OfficeDTO;
|
||||
import com.example.nto.dto.mappers.OfficeMapper;
|
||||
import com.example.nto.repository.OfficeRepository;
|
||||
import com.example.nto.service.OfficeService;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.awt.geom.Point2D;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class OfficeServiceImpl implements OfficeService {
|
||||
private final OfficeRepository officeRepository;
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<OfficeDTO> getAllOffice() {
|
||||
return officeRepository.findAll().stream().map(OfficeMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<OfficeDTO> getAllSortedDistance(double userLatitude, double userLongitude) {
|
||||
return officeRepository.findAll().stream().map(OfficeMapper::convertToDTO)
|
||||
.sorted(createComparator(new Point2D.Double(userLatitude, userLongitude))).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public OfficeDTO getById(long officeId) {
|
||||
return officeRepository.findById(officeId).map(OfficeMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с id (" + officeId + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public OfficeDTO create(OfficeDTO officeDTO) {
|
||||
return OfficeMapper.convertToDTO(officeRepository.save(OfficeMapper.convertFromDTO(officeDTO)));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public OfficeDTO update(long officeId, OfficeDTO officeDTO) {
|
||||
Office office = officeRepository.findById(officeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с id (" + officeId + ") не найден!"));
|
||||
|
||||
office.setName(officeDTO.getName());
|
||||
office.setDescription(officeDTO.getDescription());
|
||||
office.setAddress(officeDTO.getAddress());
|
||||
office.setLatitude(officeDTO.getLatitude());
|
||||
office.setLongitude(officeDTO.getLongitude());
|
||||
|
||||
// linkLogo меняется в отдельном запросе
|
||||
|
||||
office.setTelephone(officeDTO.getTelephone());
|
||||
office.setEmail(officeDTO.getEmail());
|
||||
|
||||
return OfficeMapper.convertToDTO(officeRepository.save(office));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void delete(long officeId) {
|
||||
officeRepository.findById(officeId).orElseThrow(() -> new ResourceNotFoundException("Офис с id (" + officeId + ") не найден!"));
|
||||
officeRepository.deleteById(officeId);
|
||||
}
|
||||
|
||||
private static Comparator<OfficeDTO> createComparator(Point2D point) {
|
||||
return (office0, office1) -> {
|
||||
Point2D point0 = new Point2D.Double(office0.getLatitude(), office0.getLongitude());
|
||||
Point2D point1 = new Point2D.Double(office1.getLatitude(), office1.getLongitude());
|
||||
|
||||
return Double.compare(point0.distanceSq(point), point1.distanceSq(point));
|
||||
};
|
||||
}
|
||||
}
|
@ -0,0 +1,79 @@
|
||||
package com.example.nto.service.impl;
|
||||
|
||||
import com.example.nto.aspect.annotation.LogExample;
|
||||
import com.example.nto.domain.entity.Office;
|
||||
import com.example.nto.domain.entity.Terminal;
|
||||
import com.example.nto.domain.exception.ResourceNotFoundException;
|
||||
import com.example.nto.dto.entity.TerminalDTO;
|
||||
import com.example.nto.dto.mappers.TerminalMapper;
|
||||
import com.example.nto.repository.OfficeRepository;
|
||||
import com.example.nto.repository.TerminalRepository;
|
||||
import com.example.nto.service.TerminalService;
|
||||
import com.example.nto.utils.Utils;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class TerminalServiceImpl implements TerminalService {
|
||||
private final TerminalRepository terminalRepository;
|
||||
private final OfficeRepository officeRepository;
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<TerminalDTO> getAllTerminal() {
|
||||
return terminalRepository.findAll().stream().map(TerminalMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public TerminalDTO getById(long terminalId) {
|
||||
return terminalRepository.findById(terminalId).map(TerminalMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Терминал с id (" + terminalId + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public TerminalDTO create(TerminalDTO terminalDTO) {
|
||||
Office office = officeRepository.findByName(terminalDTO.getOfficeName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с названием (" + terminalDTO.getOfficeName() + ") не найден!"));
|
||||
|
||||
Terminal terminal = new Terminal();
|
||||
terminal.setName(terminalDTO.getName());
|
||||
terminal.setOffice(office);
|
||||
|
||||
return TerminalMapper.convertToDTO(terminalRepository.save(terminal));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public TerminalDTO update(long terminalId, TerminalDTO terminalDTO) {
|
||||
Terminal terminal = terminalRepository.findById(terminalId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Терминал с id (" + terminalId + ") не найден!"));
|
||||
Office office = officeRepository.findByName(terminalDTO.getOfficeName())
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Офис с названием (" + terminalDTO.getOfficeName() + ") не найден!"));
|
||||
|
||||
terminal.setName(terminalDTO.getName());
|
||||
terminal.setCode(Utils.generateUniqueName());
|
||||
terminal.setOffice(office);
|
||||
|
||||
return TerminalMapper.convertToDTO(terminalRepository.save(terminal));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void delete(long terminalId) {
|
||||
terminalRepository.findById(terminalId).orElseThrow(() -> new ResourceNotFoundException("Терминал с id (" + terminalId + ") не найден!"));
|
||||
terminalRepository.deleteById(terminalId);
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public TerminalDTO checkCode(String code) {
|
||||
return terminalRepository.findByCode(code).map(TerminalMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Терминал с кодом (" + code + ") не найден!"));
|
||||
}
|
||||
}
|
@ -1,14 +1,24 @@
|
||||
package com.example.nto.service.impl;
|
||||
|
||||
import com.example.nto.domain.entity.Employee;
|
||||
import com.example.nto.repository.EmployeeRepository;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springframework.security.core.userdetails.UserDetails;
|
||||
import org.springframework.security.core.userdetails.UserDetailsService;
|
||||
import org.springframework.security.core.userdetails.UsernameNotFoundException;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
@Service
|
||||
@AllArgsConstructor
|
||||
public class UserDetailsServiceImpl implements UserDetailsService {
|
||||
private final EmployeeRepository employeeRepository;
|
||||
|
||||
@Override
|
||||
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
|
||||
return null;
|
||||
public UserDetails loadUserByUsername(String email) throws UsernameNotFoundException {
|
||||
Optional<Employee> employee = employeeRepository.findByEmail(email);
|
||||
if (employee.isEmpty()) throw new UsernameNotFoundException("Employee not found!");
|
||||
return employee.get();
|
||||
}
|
||||
}
|
||||
|
125
src/main/java/com/example/nto/service/impl/VisitServiceImpl.java
Normal file
@ -0,0 +1,125 @@
|
||||
package com.example.nto.service.impl;
|
||||
|
||||
import com.example.nto.aspect.annotation.LogExample;
|
||||
import com.example.nto.domain.entity.Employee;
|
||||
import com.example.nto.domain.entity.Passage;
|
||||
import com.example.nto.domain.entity.Terminal;
|
||||
import com.example.nto.domain.entity.Visit;
|
||||
import com.example.nto.domain.exception.ResourceNotFoundException;
|
||||
import com.example.nto.dto.entity.VisitDTO;
|
||||
import com.example.nto.dto.mappers.VisitMapper;
|
||||
import com.example.nto.repository.EmployeeRepository;
|
||||
import com.example.nto.repository.PassageRepository;
|
||||
import com.example.nto.repository.TerminalRepository;
|
||||
import com.example.nto.repository.VisitRepository;
|
||||
import com.example.nto.service.VisitService;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Service
|
||||
@RequiredArgsConstructor
|
||||
public class VisitServiceImpl implements VisitService {
|
||||
private final EmployeeRepository employeeRepository;
|
||||
private final VisitRepository visitRepository;
|
||||
private final TerminalRepository terminalRepository;
|
||||
private final PassageRepository passageRepository;
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<VisitDTO> getAll() {
|
||||
return visitRepository.findAll().stream().map(VisitMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<VisitDTO> getAllVisitByEmployee(long employeeId) {
|
||||
return visitRepository.findAll().stream()
|
||||
.filter(visit -> checkEmployeeVisit(visit, employeeId))
|
||||
.map(VisitMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<VisitDTO> getAllVisitByPeriod(LocalDateTime start, LocalDateTime stop) {
|
||||
// todo: Доделать если останется время
|
||||
return List.of();
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public List<VisitDTO> getAllFinished(boolean isFinished) {
|
||||
return visitRepository.findAll().stream()
|
||||
.filter(visit -> checkFinishVisit(visit, isFinished))
|
||||
.map(VisitMapper::convertToDTO).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public VisitDTO getById(long visitId) {
|
||||
return visitRepository.findById(visitId).map(VisitMapper::convertToDTO)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Посещение с id (" + visitId + ") не найден!"));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void delete(long visitId) {
|
||||
visitRepository.findById(visitId).orElseThrow(() -> new ResourceNotFoundException("Посещение с id (" + visitId + ") не найден!"));
|
||||
visitRepository.deleteById(visitId);
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public VisitDTO open(long employeeId, long startTerminalId, String passageName) {
|
||||
Employee employee = employeeRepository.findById(employeeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
Terminal terminal = terminalRepository.findById(startTerminalId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Терминал с id (" + startTerminalId + ") не найден!"));
|
||||
Passage passage = passageRepository.findByPassageName(passageName)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Тип входа с названием (" + passageName + ") не найден!"));
|
||||
|
||||
Visit visit = new Visit();
|
||||
|
||||
visit.setEmployee(employee);
|
||||
visit.setStartVisit(LocalDateTime.now());
|
||||
visit.setFinished(false);
|
||||
visit.setStartTerminal(terminal);
|
||||
visit.setPassage(passage);
|
||||
|
||||
return VisitMapper.convertToDTO(visitRepository.save(visit));
|
||||
}
|
||||
|
||||
@Override
|
||||
@LogExample
|
||||
public void exit(long employeeId, long endTerminalId) {
|
||||
Employee employee = employeeRepository.findById(employeeId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Работник с id (" + employeeId + ") не найден!"));
|
||||
Terminal terminal = terminalRepository.findById(endTerminalId)
|
||||
.orElseThrow(() -> new ResourceNotFoundException("Терминал с id (" + endTerminalId + ") не найден!"));
|
||||
Visit activeVisit = getActiveVisit(employee);
|
||||
|
||||
activeVisit.setStartVisit(LocalDateTime.now());
|
||||
activeVisit.setFinished(true);
|
||||
activeVisit.setEndTerminal(terminal);
|
||||
|
||||
visitRepository.save(activeVisit);
|
||||
}
|
||||
|
||||
private static boolean checkEmployeeVisit(Visit visit, long employeeId) {
|
||||
return visit.getEmployee().getId() == employeeId;
|
||||
}
|
||||
|
||||
private static boolean checkFinishVisit(Visit visit, boolean isFinished) {
|
||||
return visit.isFinished() == isFinished;
|
||||
}
|
||||
|
||||
private static Visit getActiveVisit(Employee employee) {
|
||||
List<Visit> visits = employee.getVisits().stream().filter(Visit::isFinished).collect(Collectors.toList());
|
||||
|
||||
if (visits.size() == 1) return visits.get(0);
|
||||
else throw new IllegalStateException("Пользователь не может находится в суперпозиции");
|
||||
}
|
||||
}
|