Compare commits

..

7 Commits

21 changed files with 434 additions and 48 deletions

View File

@ -0,0 +1,17 @@
package github.benjamin.equipreservebackend.constant;
import lombok.Getter;
@Getter
public enum ApprovalStep {
LEADER(1),
DEVICE_ADMIN(2);
final Integer step;
ApprovalStep(Integer step) {
this.step = step;
}
}

View File

@ -1,12 +1,21 @@
package github.benjamin.equipreservebackend.constant;
import lombok.Getter;
/**
* 设备内部状态
*/
@Getter
public enum DeviceStatus {
AVAILABLE,
MAINTENANCE,
DISABLED
AVAILABLE("可用"),
MAINTENANCE("维护中"),
DISABLED("停用");
final String label;
DeviceStatus(String label) {
this.label = label;
}
}

View File

@ -7,8 +7,8 @@ public enum ReservationStatus {
PENDING_LEADER("团队负责人审批中"),
PENDING_DEVICE_ADMIN("设备负责人审批中"),
APPROVED("通过"),
APPROVED_ASSIST("需要协助实验"),
REJECTED("审批不通过");
APPROVED_ASSIST("通过,需要协助实验"),
REJECTED("不通过");
final String label;

View File

@ -0,0 +1,39 @@
package github.benjamin.equipreservebackend.controller;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.dto.LeaderApprovalDTO;
import github.benjamin.equipreservebackend.entity.Approval;
import github.benjamin.equipreservebackend.response.ResponseResult;
import github.benjamin.equipreservebackend.service.ApprovalService;
import github.benjamin.equipreservebackend.vo.LeaderApprovalVO;
import lombok.RequiredArgsConstructor;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;
@RestController
@RequestMapping("/approval")
@RequiredArgsConstructor
public class ApprovalController {
private final ApprovalService approvalService;
@PreAuthorize("hasAnyRole('LEADER', 'DEVICE_ADMIN')")
@PostMapping
public ResponseResult<?> addApproval(@RequestBody LeaderApprovalDTO dto) {
approvalService.addApproval(dto);
return ResponseResult.success();
}
@PreAuthorize("hasAnyRole('LEADER', 'DEVICE_ADMIN')")
@GetMapping("/{id}")
public ResponseResult<IPage<LeaderApprovalVO>> getApproval(@PathVariable("id") Long id,
@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size,
@RequestParam(required = false) String applicantName,
@RequestParam(required = false) String deviceName) {
Page<Approval> pageRequest = new Page<>(page, size);
return ResponseResult.success(approvalService.getApproval(pageRequest, id, applicantName, deviceName));
}
}

View File

@ -5,6 +5,7 @@ import github.benjamin.equipreservebackend.entity.Device;
import github.benjamin.equipreservebackend.response.ResponseResult;
import github.benjamin.equipreservebackend.service.DeviceService;
import github.benjamin.equipreservebackend.service.ReservationService;
import github.benjamin.equipreservebackend.vo.DeviceAdminVO;
import github.benjamin.equipreservebackend.vo.DeviceUserVO;
import github.benjamin.equipreservebackend.vo.TimeRangeVO;
import lombok.RequiredArgsConstructor;
@ -26,16 +27,16 @@ public class DeviceController {
@PreAuthorize("hasRole('USER')")
@GetMapping
public ResponseResult<Page<DeviceUserVO>> getDevices(@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size,
@RequestParam(required = false) String name) {
public ResponseResult<Page<DeviceUserVO>> getUserDevices(@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size,
@RequestParam(required = false) String name) {
Page<Device> pageRequest = new Page<>(page, size);
Page<DeviceUserVO> res = deviceService.getDeviceVO(pageRequest, name);
Page<DeviceUserVO> res = deviceService.getUserDevices(pageRequest, name);
return ResponseResult.success(res);
}
@PreAuthorize("hasRole('USER')")
@GetMapping ("/unavailable-times/{id}")
@GetMapping("/unavailable-times/{id}")
public ResponseResult<List<TimeRangeVO>> getUnavailableTimes(@PathVariable Long id) {
List<TimeRangeVO> res = reservationService.getUnavailableTimes(id);
return ResponseResult.success(res);
@ -43,7 +44,7 @@ public class DeviceController {
@PreAuthorize("hasRole('DEVICE_ADMIN')")
@PostMapping
public ResponseResult<?> addDevice(@RequestBody Device device){
public ResponseResult<?> addDevice(@RequestBody Device device) {
deviceService.addDevice(device);
return ResponseResult.success(device);
}
@ -64,6 +65,17 @@ public class DeviceController {
return ResponseResult.success(updatedDevice);
}
@PreAuthorize("hasRole('DEVICE_ADMIN')")
@GetMapping("/{userId}")
public ResponseResult<Page<DeviceAdminVO>> getAdminDevice(@PathVariable("userId") Long userId,
@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size,
@RequestParam(required = false) String name) {
Page<Device> pageRequest = new Page<>(page, size);
return ResponseResult.success(deviceService.getAdminDevice(pageRequest, userId, name));
}
@PreAuthorize("hasRole('DEVICE_ADMIN')")
@PostMapping("/{id}/image")
public ResponseResult<?> uploadImage(@PathVariable("id") Long id,

View File

@ -4,6 +4,7 @@ import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.response.ResponseResult;
import github.benjamin.equipreservebackend.service.ReservationService;
import github.benjamin.equipreservebackend.vo.ReservationVO;
import github.benjamin.equipreservebackend.vo.UserReservationVO;
import lombok.RequiredArgsConstructor;
import org.springframework.security.access.prepost.PreAuthorize;
@ -26,11 +27,19 @@ public class ReservationController {
@PreAuthorize("hasRole('USER')")
@GetMapping("/{userId}")
public ResponseResult<Page<UserReservationVO>> getUserReservation(@PathVariable("userId") Long userId,
@RequestParam(defaultValue = "10") Integer page,
@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size) {
Page<Reservation> pageRequest = new Page<>(page, size);
Page<UserReservationVO> res = reservationService.getUserReservationVO(userId, pageRequest);
return ResponseResult.success(res);
}
@PreAuthorize("hasAnyRole('LEADER', 'DEVICE_ADMIN')")
@GetMapping("/approval/{id}")
public ResponseResult<Page<ReservationVO>> getReservation(@PathVariable("id") Long id,
@RequestParam(defaultValue = "1") Integer page,
@RequestParam(defaultValue = "10") Integer size) {
return ResponseResult.success(reservationService.getReservationVO(id, page, size));
}
}

View File

@ -0,0 +1,13 @@
package github.benjamin.equipreservebackend.dto;
import lombok.Data;
@Data
public class LeaderApprovalDTO {
private Long userId;
private Long reservationId;
private Boolean isApprove;
private Boolean needAssist;
}

View File

@ -1,12 +1,18 @@
package github.benjamin.equipreservebackend.entity;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.time.LocalDateTime;
@Data
@TableName("approvals")
@NoArgsConstructor
@AllArgsConstructor
@Builder
public class Approval {
private Long id;

View File

@ -0,0 +1,19 @@
package github.benjamin.equipreservebackend.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.entity.Approval;
import github.benjamin.equipreservebackend.vo.LeaderApprovalVO;
import org.apache.ibatis.annotations.Param;
import org.springframework.stereotype.Repository;
@Repository
public interface ApprovalMapper extends BaseMapper<Approval> {
IPage<LeaderApprovalVO> getApproval(Page<?> page,
@Param("approverId") Long approverId,
@Param("applicantName") String applicantName,
@Param("deviceName") String deviceName);
}

View File

@ -0,0 +1,13 @@
package github.benjamin.equipreservebackend.service;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.dto.LeaderApprovalDTO;
import github.benjamin.equipreservebackend.entity.Approval;
import github.benjamin.equipreservebackend.vo.LeaderApprovalVO;
public interface ApprovalService {
void addApproval(LeaderApprovalDTO dto);
IPage<LeaderApprovalVO> getApproval(Page<Approval> pageRequest, Long userId, String applicantName, String deviceName);
}

View File

@ -1,14 +1,16 @@
package github.benjamin.equipreservebackend.service;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.entity.Device;
import github.benjamin.equipreservebackend.vo.DeviceAdminVO;
import github.benjamin.equipreservebackend.vo.DeviceUserVO;
import org.springframework.web.multipart.MultipartFile;
import java.io.IOException;
public interface DeviceService {
Page<DeviceUserVO> getDeviceVO(Page<Device> pageRequest, String name);
Page<DeviceUserVO> getUserDevices(Page<Device> pageRequest, String name);
void addDevice(Device device);
@ -17,4 +19,13 @@ public interface DeviceService {
Device updateDevice(Device device);
String saveImage(Long id, MultipartFile image) throws IOException;
/**
* 获取用户所属团队的所有设备
* @param pageRequest
* @param userId
* @param name
* @return 分页后的设备列表
*/
Page<DeviceAdminVO> getAdminDevice(Page<Device> pageRequest, Long userId, String name);
}

View File

@ -2,6 +2,7 @@ package github.benjamin.equipreservebackend.service;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.vo.ReservationVO;
import github.benjamin.equipreservebackend.vo.TimeRangeVO;
import github.benjamin.equipreservebackend.vo.UserReservationVO;
@ -16,4 +17,6 @@ public interface ReservationService {
Page<UserReservationVO> getUserReservationVO(Long userId, Page<Reservation> pageRequest);
List<TimeRangeVO> getUnavailableTimes(Long id);
Page<ReservationVO> getReservationVO(Long userId, Integer page, Integer size);
}

View File

@ -0,0 +1,68 @@
package github.benjamin.equipreservebackend.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.constant.ApprovalStep;
import github.benjamin.equipreservebackend.constant.ReservationStatus;
import github.benjamin.equipreservebackend.dto.LeaderApprovalDTO;
import github.benjamin.equipreservebackend.entity.Approval;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.entity.Role;
import github.benjamin.equipreservebackend.exception.ApiException;
import github.benjamin.equipreservebackend.mapper.ApprovalMapper;
import github.benjamin.equipreservebackend.mapper.ReservationMapper;
import github.benjamin.equipreservebackend.mapper.RoleMapper;
import github.benjamin.equipreservebackend.service.ApprovalService;
import github.benjamin.equipreservebackend.vo.LeaderApprovalVO;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
@RequiredArgsConstructor
public class ApprovalServiceImpl implements ApprovalService {
private final ApprovalMapper approvalMapper;
private final ReservationMapper reservationMapper;
private final RoleMapper roleMapper;
@Override
public void addApproval(LeaderApprovalDTO dto) {
List<Role> userRoles = roleMapper.selectRoleByUserId(dto.getUserId());
final ApprovalStep step;
final ReservationStatus status;
if (userRoles.stream().anyMatch(r -> r.getCode().equals("LEADER"))) {
step = ApprovalStep.LEADER;
status = dto.getIsApprove() ? ReservationStatus.PENDING_DEVICE_ADMIN : ReservationStatus.REJECTED;
} else if (userRoles.stream().anyMatch(r -> r.getCode().equals("DEVICE_ADMIN"))){
step = ApprovalStep.DEVICE_ADMIN;
if (dto.getIsApprove()) {
status = dto.getNeedAssist() ? ReservationStatus.APPROVED_ASSIST : ReservationStatus.APPROVED;
} else {
status = ReservationStatus.REJECTED;
}
} else {
throw new ApiException("用户角色不匹配,请核对或联系开发人员");
}
Approval approval = Approval.builder()
.approverId(dto.getUserId())
.reservationId(dto.getReservationId())
.step(step.getStep())
.decision(dto.getIsApprove() ? 1 : 0)
.build();
approvalMapper.insert(approval);
reservationMapper.update(new LambdaUpdateWrapper<Reservation>()
.eq(Reservation::getId, dto.getReservationId())
.set(Reservation::getStatus, status));
}
@Override
public IPage<LeaderApprovalVO> getApproval(Page<Approval> pageRequest, Long userId, String applicantName, String deviceName) {
return approvalMapper.getApproval(pageRequest, userId, applicantName, deviceName);
}
}

View File

@ -7,13 +7,16 @@ import github.benjamin.equipreservebackend.constant.DeviceReservationState;
import github.benjamin.equipreservebackend.constant.DeviceStatus;
import github.benjamin.equipreservebackend.entity.Device;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.entity.User;
import github.benjamin.equipreservebackend.exception.ApiException;
import github.benjamin.equipreservebackend.mapper.DeviceMapper;
import github.benjamin.equipreservebackend.mapper.UserMapper;
import github.benjamin.equipreservebackend.response.ResponseCode;
import github.benjamin.equipreservebackend.service.DeviceService;
import github.benjamin.equipreservebackend.service.ReservationService;
import github.benjamin.equipreservebackend.utils.FileUtil;
import github.benjamin.equipreservebackend.utils.PageUtil;
import github.benjamin.equipreservebackend.vo.DeviceAdminVO;
import github.benjamin.equipreservebackend.vo.DeviceUserVO;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
@ -26,6 +29,7 @@ import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
@ -37,8 +41,10 @@ public class DeviceServiceImpl implements DeviceService {
private final ReservationService reservationService;
private final UserMapper userMapper;
@Override
public Page<DeviceUserVO> getDeviceVO(Page<Device> pageRequest, String name) {
public Page<DeviceUserVO> getUserDevices(Page<Device> pageRequest, String name) {
LambdaQueryWrapper<Device> queryWrapper = new LambdaQueryWrapper<Device>()
.eq(Device::getStatus, DeviceStatus.AVAILABLE)
.orderByAsc(Device::getName);
@ -49,11 +55,15 @@ public class DeviceServiceImpl implements DeviceService {
List<Long> deviceIds = devices.getRecords().stream()
.map(Device::getId)
.toList();
Page<DeviceUserVO> res = PageUtil.copyPage(devices);
if (deviceIds.isEmpty()) {
res.setRecords(new ArrayList<>());
return res;
}
List<Reservation> reservations = reservationService.getApprovedReservationsByDeviceIds(deviceIds);
List<DeviceUserVO> deviceUserVOS = devices.getRecords().stream()
.map(device -> buildDeviceVO(device, reservations))
.toList();
Page<DeviceUserVO> res = PageUtil.copyPage(devices);
res.setRecords(deviceUserVOS);
return res;
}
@ -121,6 +131,21 @@ public class DeviceServiceImpl implements DeviceService {
return imagePath;
}
@Override
public Page<DeviceAdminVO> getAdminDevice(Page<Device> pageRequest, Long userId, String name) {
User user = userMapper.selectById(userId);
LambdaQueryWrapper<Device> wrapper = new LambdaQueryWrapper<Device>()
.eq(Device::getTeamId, user.getTeamId())
.orderByAsc(Device::getName);
if (StringUtils.hasText(name)) {
wrapper.like(Device::getName, name);
}
Page<Device> devicePage = deviceMapper.selectPage(pageRequest, wrapper);
Page<DeviceAdminVO> res = PageUtil.copyPage(devicePage);
res.setRecords(devicePage.getRecords().stream().map(DeviceAdminVO::new).toList());
return res;
}
private DeviceUserVO buildDeviceVO(Device device, List<Reservation> reservations) {
DeviceUserVO vo = new DeviceUserVO(device);
// TODO 显示设备状态逻辑根据客户需求修改

View File

@ -3,16 +3,12 @@ package github.benjamin.equipreservebackend.service.impl;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import github.benjamin.equipreservebackend.constant.ReservationStatus;
import github.benjamin.equipreservebackend.entity.Device;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.entity.Team;
import github.benjamin.equipreservebackend.entity.User;
import github.benjamin.equipreservebackend.mapper.DeviceMapper;
import github.benjamin.equipreservebackend.mapper.ReservationMapper;
import github.benjamin.equipreservebackend.mapper.TeamMapper;
import github.benjamin.equipreservebackend.mapper.UserMapper;
import github.benjamin.equipreservebackend.entity.*;
import github.benjamin.equipreservebackend.exception.ApiException;
import github.benjamin.equipreservebackend.mapper.*;
import github.benjamin.equipreservebackend.service.ReservationService;
import github.benjamin.equipreservebackend.utils.PageUtil;
import github.benjamin.equipreservebackend.vo.ReservationVO;
import github.benjamin.equipreservebackend.vo.TimeRangeVO;
import github.benjamin.equipreservebackend.vo.UserReservationVO;
import lombok.RequiredArgsConstructor;
@ -20,7 +16,6 @@ import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;
import java.util.Objects;
@ -39,6 +34,8 @@ public class ReservationServiceImpl implements ReservationService {
private final TeamMapper teamMapper;
private final RoleMapper roleMapper;
/**
* 未来days天内有预约的设备显示为有预约
*/
@ -93,19 +90,14 @@ public class ReservationServiceImpl implements ReservationService {
Page<UserReservationVO> res = PageUtil.copyPage(reservations);
List<UserReservationVO> vos;
if (deviceAdminIDs.isEmpty()) {
vos = reservations.getRecords().stream()
.map(reservation -> new UserReservationVO(reservation, deviceNameMap))
.toList();
} else {
Map<Long, User> deviceAdminMap = userMapper.selectList(new LambdaQueryWrapper<User>()
.in(User::getId, deviceAdminIDs))
.stream()
.collect(Collectors.toMap(User::getId, Function.identity()));
vos = reservations.getRecords().stream()
.map(reservation -> new UserReservationVO(reservation, deviceNameMap, deviceAdminMap))
.toList();
}
Map<Long, User> deviceAdminMap = userMapper.selectList(new LambdaQueryWrapper<User>()
.in(User::getId, deviceAdminIDs))
.stream()
.collect(Collectors.toMap(User::getId, Function.identity()));
vos = reservations.getRecords().stream()
.map(reservation -> new UserReservationVO(reservation, deviceNameMap, deviceAdminMap))
.toList();
res.setRecords(vos);
return res;
}
@ -121,4 +113,33 @@ public class ReservationServiceImpl implements ReservationService {
.map(r -> new TimeRangeVO(r.getStartTime(), r.getEndTime()))
.toList();
}
@Override
public Page<ReservationVO> getReservationVO(Long userId, Integer page, Integer size) {
User user = userMapper.selectById(userId);
List<Device> devices = deviceMapper.selectList(new LambdaQueryWrapper<Device>()
.eq(Device::getTeamId, user.getTeamId())
.select());
List<Role> userRole = roleMapper.selectRoleByUserId(userId);
ReservationStatus status;
if (userRole.stream().anyMatch(r -> r.getCode().equals("LEADER"))) {
status = ReservationStatus.PENDING_LEADER;
} else if (userRole.stream().anyMatch(r -> r.getCode().equals("DEVICE_ADMIN"))) {
status = ReservationStatus.PENDING_DEVICE_ADMIN;
} else {
throw new ApiException("用户角色不正确,请检查或联系开发人员");
}
List<Long> deviceIds = devices.stream().map(Device::getId).toList();
Map<Long, Device> deviceMap = devices.stream().collect(Collectors.toMap(Device::getId, Function.identity()));
Page<Reservation> reservationPage = reservationMapper.selectPage(new Page<>(page, size), new LambdaQueryWrapper<Reservation>()
.in(Reservation::getDeviceId, deviceIds)
.eq(Reservation::getStatus, status)
.orderByDesc(Reservation::getCreatedTime));
Page<ReservationVO> res = PageUtil.copyPage(reservationPage);
res.setRecords(reservationPage.getRecords().stream()
.map(r -> new ReservationVO(r, deviceMap.get(r.getDeviceId())))
.toList());
return res;
}
}

View File

@ -0,0 +1,29 @@
package github.benjamin.equipreservebackend.vo;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import github.benjamin.equipreservebackend.constant.DeviceStatus;
import github.benjamin.equipreservebackend.entity.Device;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
public class DeviceAdminVO {
@JsonSerialize(using = ToStringSerializer.class)
private Long deviceId;
private String name;
private String usageRequirement;
private String location;
private String imagePath;
private String status;
public DeviceAdminVO(Device d) {
this.deviceId = d.getId();
this.name = d.getName();
this.usageRequirement = d.getUsageRequirement();
this.location = d.getLocation();
this.imagePath = d.getImagePath();
this.status = d.getStatus();
}
}

View File

@ -0,0 +1,23 @@
package github.benjamin.equipreservebackend.vo;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import lombok.Data;
import java.time.LocalDate;
@Data
public class LeaderApprovalVO {
@JsonSerialize(using = ToStringSerializer.class)
private Long approvalId;
private String applicantName;
private String applicantTeam;
private String applicantContact;
private String deviceName;
private LocalDate startTime;
private LocalDate endTime;
private Integer decision;
private String status;
}

View File

@ -0,0 +1,42 @@
package github.benjamin.equipreservebackend.vo;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.fasterxml.jackson.databind.ser.std.StringSerializer;
import com.fasterxml.jackson.databind.ser.std.ToStringSerializer;
import github.benjamin.equipreservebackend.entity.Device;
import github.benjamin.equipreservebackend.entity.Reservation;
import github.benjamin.equipreservebackend.entity.User;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.time.LocalDate;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class ReservationVO {
@JsonSerialize(using = ToStringSerializer.class)
private Long reservationId;
private String applicantName;
private String applicantTeam;
private String applicantContact;
@JsonSerialize(using = ToStringSerializer.class)
private Long deviceId;
private String deviceName;
private LocalDate startTime;
private LocalDate endTime;
public ReservationVO(Reservation r, Device d) {
this.reservationId = r.getId();
this.applicantName = r.getApplicantName();
this.applicantTeam = r.getApplicantTeam();
this.applicantContact = r.getApplicantContact();
this.deviceId = d.getId();
this.deviceName = d.getName();
this.startTime = r.getStartTime();
this.endTime = r.getEndTime();
}
}

View File

@ -24,23 +24,17 @@ public class UserReservationVO {
private String deviceAdminContact;
private LocalDateTime createdTime;
public UserReservationVO(Reservation r, Map<Long, String> deviceNameMap) {
public UserReservationVO(Reservation r, Map<Long, String> deviceNameMap, Map<Long, User> deviceAdminMap) {
this.reservationId = r.getId().toString();
this.deviceName = deviceNameMap.get(r.getDeviceId());
this.startTime = r.getStartTime();
this.endTime = r.getEndTime();
this.statusLabel = ReservationStatus.valueOf(r.getStatus()).getLabel();
User deviceAdmin = deviceAdminMap.get(r.getDeviceAdminId());
this.deviceAdminName = deviceAdmin.getName();
this.deviceAdminContact = deviceAdmin.getPhone();
this.createdTime = r.getCreatedTime();
}
public UserReservationVO(Reservation r, Map<Long, String> deviceNameMap, Map<Long, User> deviceAdminMap) {
this(r, deviceNameMap);
ReservationStatus status = ReservationStatus.valueOf(r.getStatus());
if (status == ReservationStatus.APPROVED_ASSIST) {
User deviceAdmin = deviceAdminMap.get(r.getDeviceAdminId());
this.deviceAdminName = deviceAdmin.getName();
this.deviceAdminContact = deviceAdmin.getPhone();
}
}
}

View File

@ -6,3 +6,14 @@ spring:
username: your-username
password: your-password
url: jdbc:mysql://127.0.0.1:3306/equip_reserve?serverTimeZone=UTC
server:
port: 8080
jwt:
secret: your-secret
equip-reserve:
device-days: 7
allowed-origins: http://localhost:5173
mybatis-plus:
mapper-locations: classpath:mapper/*.xml
configuration:
map-underscore-to-camel-case: true

View File

@ -0,0 +1,22 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="github.benjamin.equipreservebackend.mapper.ApprovalMapper">
<select id="getApproval" resultType="github.benjamin.equipreservebackend.vo.LeaderApprovalVO">
SELECT a.id as approvalId, r.applicant_name, r.applicant_team, r.applicant_contact, d.name as deviceName, r.start_time, r.end_time, a.decision, r.status
FROM approvals a
LEFT JOIN reservations r ON a.reservation_id = r.id
LEFT JOIN devices d ON r.device_id = d.id
WHERE a.approver_id = #{approverId}
<if test="applicantName != null and applicantName != ''">
AND r.applicant_name LIKE CONCAT('%', #{applicantName}, '%')
</if>
<if test="deviceName != null and deviceName != ''">
AND d.name LIKE CONCAT('%', #{deviceName}, '%')
</if>
ORDER BY a.timestamp DESC
</select>
</mapper>