Raid Layout page working

This commit is contained in:
2025-03-09 12:15:34 -04:00
parent 01c27d0c5a
commit 63486457fe
16 changed files with 459 additions and 0 deletions

View File

@@ -0,0 +1,37 @@
CREATE TABLE raid_builder.raid_layout(
raid_layout_id uuid PRIMARY KEY,
raid_group_id uuid REFERENCES raid_builder.raid_group(raid_group_id) NOT NULL,
raid_layout_name text NOT NULL,
raid_size int NOT NULL,
--Auditing
modified_by uuid,
modified_date timestamptz,
created_by uuid NOT NULL,
created_date timestamptz NOT NULL
);
CREATE INDEX idx_raid_layout_raid_group_id ON raid_builder.raid_layout(raid_group_id);
CREATE INDEX idx_raid_layout_raid_layout_name ON raid_builder.raid_layout(raid_layout_name);
GRANT ALL ON TABLE raid_builder.raid_layout TO raid_builder;
CREATE TABLE raid_builder.raid_layout_class_group_xref(
raid_layout_class_group_xref_id uuid PRIMARY KEY,
raid_layout_id uuid REFERENCES raid_builder.raid_layout(raid_layout_id) NOT NULL,
class_group_id uuid REFERENCES raid_builder.class_group(class_group_id) NOT NULL,
layout_location int NOT NULL,
--Auditing
modified_by uuid,
modified_date timestamptz,
created_by uuid NOT NULL,
created_date timestamptz NOT NULL
);
CREATE INDEX idx_raid_layout_class_group_xref_raid_layout_id ON raid_builder.raid_layout_class_group_xref(raid_layout_id);
CREATE INDEX idx_raid_layout_class_group_xref_class_group_id ON raid_builder.raid_layout_class_group_xref(class_group_id);
GRANT ALL ON TABLE raid_builder.raid_layout_class_group_xref TO raid_builder;

View File

@@ -89,6 +89,15 @@ public class ClassGroupController{
return classGroupService.getClassGroup(classGroupId, raidGroupId);
}
@GetMapping("/raidLayout/{raidLayoutId}")
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER, RaidGroupPermissionType.RAIDER})
public List<ClassGroup> getClassGroupsByRaidLayoutId(@PathVariable("raidGroupId") UUID raidGroupId, @PathVariable("raidLayoutId") UUID raidLayoutId){
log.info("Getting class groups for raid layout {} for raid group {}", raidLayoutId, raidGroupId);
return classGroupService.getClassGroupsByRaidLayoutId(raidLayoutId);
}
@PostMapping
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})

View File

@@ -0,0 +1,133 @@
package com.mattrixwv.raidbuilder.controller;
import java.util.List;
import java.util.UUID;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;
import com.mattrixwv.raidbuilder.annotation.AccountAuthorization;
import com.mattrixwv.raidbuilder.annotation.RaidGroupAuthorization;
import com.mattrixwv.raidbuilder.entity.RaidLayout;
import com.mattrixwv.raidbuilder.entity.RaidLayoutClassGroupXref;
import com.mattrixwv.raidbuilder.service.RaidLayoutService;
import com.mattrixwv.raidbuilder.util.DatabaseTypeUtil.AccountPermissionType;
import com.mattrixwv.raidbuilder.util.DatabaseTypeUtil.RaidGroupPermissionType;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
@Slf4j
@RestController
@RequestMapping("/raidGroup/{raidGroupId}/raidLayout")
@RequiredArgsConstructor
public class RaidLayoutController{
private final ObjectMapper mapper;
private final RaidLayoutService raidLayoutService;
@GetMapping
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER, RaidGroupPermissionType.RAIDER})
public List<RaidLayout> getRaidLayouts(@PathVariable("raidGroupId") UUID raidGroupId, @RequestParam("page") int page, @RequestParam("pageSize") int pageSize, @RequestParam(name = "searchTerm", required = false) String searchTerm){
log.info("Getting Raid Layouts for Raid Group {} on page {} of size {} with search {}", raidGroupId, page, pageSize, searchTerm);
List<RaidLayout> raidLayouts = searchTerm == null ?
raidLayoutService.getRaidLayoutsByRaidGroupId(raidGroupId, page, pageSize) :
raidLayoutService.getRaidLayoutsByRaidGroupId(raidGroupId, page, pageSize, searchTerm);
return raidLayouts;
}
@GetMapping("/count")
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER, RaidGroupPermissionType.RAIDER})
public ObjectNode getRaidLayoutCount(@PathVariable("raidGroupId") UUID raidGroupId, @RequestParam(name = "searchTerm", required = false) String searchTerm){
log.info("Getting Raid Layout Count for Raid Group {} with search {}", raidGroupId, searchTerm);
long count = searchTerm == null ?
raidLayoutService.getRaidLayoutCountByRaidGroupId(raidGroupId) :
raidLayoutService.getRaidLayoutCountByRaidGroupId(raidGroupId, searchTerm);
ObjectNode returnNode = mapper.createObjectNode();
returnNode.put("count", count);
returnNode.put("status", "success");
return returnNode;
}
@PostMapping
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER})
public ObjectNode createRaidLayout(@PathVariable("raidGroupId") UUID raidGroupId, @RequestBody ObjectNode bodyNode){
log.info("Creating Raid Layout for Raid Group {}", raidGroupId);
RaidLayout raidLayout = mapper.convertValue(bodyNode.get("raidLayout"), RaidLayout.class);
raidLayout.setRaidGroupId(raidGroupId);
RaidLayoutClassGroupXref[] xrefsArray = mapper.convertValue(bodyNode.get("raidLayoutClassGroupXrefs"), RaidLayoutClassGroupXref[].class);
List<RaidLayoutClassGroupXref> xrefs = List.of(xrefsArray);
raidLayout = raidLayoutService.createRaidLayout(raidLayout, xrefs);
ObjectNode returnNode = mapper.createObjectNode();
returnNode.put("raidLayoutId", raidLayout.getRaidLayoutId().toString());
returnNode.put("status", "success");
return returnNode;
}
@PutMapping("/{raidLayoutId}")
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER})
public ObjectNode updateRaidLayout(@PathVariable("raidGroupId") UUID raidGroupId, @PathVariable("raidLayoutId") UUID raidLayoutId, @RequestBody ObjectNode bodyNode){
log.info("Updating Raid Layout {} for Raid Group {}", raidLayoutId, raidGroupId);
RaidLayout raidLayout = mapper.convertValue(bodyNode.get("raidLayout"), RaidLayout.class);
raidLayout.setRaidGroupId(raidGroupId);
raidLayout.setRaidLayoutId(raidLayoutId);
RaidLayoutClassGroupXref[] xrefsArray = mapper.convertValue(bodyNode.get("raidLayoutClassGroupXrefs"), RaidLayoutClassGroupXref[].class);
List<RaidLayoutClassGroupXref> xrefs = List.of(xrefsArray);
raidLayoutService.updateRaidLayout(raidLayout, xrefs);
ObjectNode returnNode = mapper.createObjectNode();
returnNode.put("raidLayoutId", raidLayout.getRaidLayoutId().toString());
returnNode.put("status", "success");
return returnNode;
}
@DeleteMapping("/{raidLayoutId}")
@AccountAuthorization(permissions = {AccountPermissionType.ADMIN, AccountPermissionType.USER})
@RaidGroupAuthorization(permissions = {RaidGroupPermissionType.ADMIN, RaidGroupPermissionType.LEADER})
public ObjectNode deleteRaidLayout(@PathVariable("raidGroupId") UUID raidGroupId, @PathVariable("raidLayoutId") UUID raidLayoutId){
log.info("Deleting Raid Layout {} for Raid Group {}", raidLayoutId, raidGroupId);
raidLayoutService.deleteRaidLayout(raidLayoutId, raidGroupId);
ObjectNode returnNode = mapper.createObjectNode();
returnNode.put("status", "success");
return returnNode;
}
}

View File

@@ -0,0 +1,33 @@
package com.mattrixwv.raidbuilder.entity;
import java.util.UUID;
import jakarta.persistence.Column;
import jakarta.persistence.Entity;
import jakarta.persistence.GeneratedValue;
import jakarta.persistence.GenerationType;
import jakarta.persistence.Id;
import jakarta.persistence.Table;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.NoArgsConstructor;
@Entity
@Table(name = "raid_layout", schema = "raid_builder")
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class RaidLayout extends AuditableEntity{
@Id
@Column(name = "raid_layout_id")
@GeneratedValue(strategy = GenerationType.UUID)
private UUID raidLayoutId;
@Column(name = "raid_group_id")
private UUID raidGroupId;
@Column(name = "raid_layout_name")
private String raidLayoutName;
@Column(name = "raid_size")
private int raidSize;
}

View File

@@ -0,0 +1,41 @@
package com.mattrixwv.raidbuilder.entity;
import java.util.UUID;
import jakarta.persistence.Column;
import jakarta.persistence.Entity;
import jakarta.persistence.FetchType;
import jakarta.persistence.GeneratedValue;
import jakarta.persistence.GenerationType;
import jakarta.persistence.Id;
import jakarta.persistence.JoinColumn;
import jakarta.persistence.OneToOne;
import jakarta.persistence.Table;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.NoArgsConstructor;
@Entity
@Table(name = "raid_layout_class_group_xref", schema = "raid_builder")
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class RaidLayoutClassGroupXref extends AuditableEntity{
@Id
@Column(name = "raid_layout_class_group_xref_id")
@GeneratedValue(strategy = GenerationType.UUID)
private UUID raidLayoutClassGroupXrefId;
@Column(name = "raid_layout_id")
private UUID raidLayoutId;
@Column(name = "class_group_id")
private UUID classGroupId;
@Column(name = "layout_location")
private int layoutLocation;
@OneToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "class_group_id", referencedColumnName = "class_group_id", insertable = false, updatable = false)
private ClassGroup classGroup;
}

View File

@@ -1,5 +1,12 @@
package com.mattrixwv.raidbuilder.repository.class_group;
import java.util.List;
import java.util.UUID;
import com.mattrixwv.raidbuilder.entity.ClassGroup;
public interface ClassGroupCustomRepository{
public List<ClassGroup> findAllByRaidLayoutId(UUID raidLayoutId);
}

View File

@@ -1,9 +1,41 @@
package com.mattrixwv.raidbuilder.repository.class_group;
import java.util.List;
import java.util.UUID;
import org.springframework.stereotype.Repository;
import com.mattrixwv.raidbuilder.entity.ClassGroup;
import com.mattrixwv.raidbuilder.entity.RaidLayoutClassGroupXref;
import jakarta.persistence.EntityManager;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
@Slf4j
@Repository
@RequiredArgsConstructor
public class ClassGroupRepositoryImpl implements ClassGroupCustomRepository{
private final EntityManager entityManager;
@Override
public List<ClassGroup> findAllByRaidLayoutId(UUID raidLayoutId){
String selectString = """
SELECT xref FROM RaidLayoutClassGroupXref xref
LEFT JOIN FETCH xref.classGroup cg
WHERE xref.raidLayoutId = :raidLayoutId
ORDER BY xref.layoutLocation
""";
List<RaidLayoutClassGroupXref> xrefs = entityManager.createQuery(selectString, RaidLayoutClassGroupXref.class)
.setParameter("raidLayoutId", raidLayoutId)
.getResultList();
List<ClassGroup> classGroups = xrefs.stream().map(RaidLayoutClassGroupXref::getClassGroup).toList();
return classGroups;
}
}

View File

@@ -0,0 +1,5 @@
package com.mattrixwv.raidbuilder.repository.raid_layout;
public interface RaidLayoutCustomRepository{
}

View File

@@ -0,0 +1,28 @@
package com.mattrixwv.raidbuilder.repository.raid_layout;
import java.util.List;
import java.util.UUID;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.jpa.repository.JpaRepository;
import com.mattrixwv.raidbuilder.entity.RaidLayout;
public interface RaidLayoutRepository extends RaidLayoutCustomRepository, JpaRepository<RaidLayout, UUID>{
public void deleteByRaidLayoutIdAndRaidGroupId(UUID raidLayoutId, UUID raidGroupId);
public void deleteAllByRaidGroupId(UUID raidGroupId);
public void deleteAllByRaidGroupIdIn(Iterable<UUID> raidGroupIds);
public RaidLayout findByRaidLayoutIdAndRaidGroupId(UUID raidLayoutId, UUID raidGroupId);
public List<RaidLayout> findAllByRaidGroupId(UUID raidGroupId);
public List<RaidLayout> findAllByRaidGroupId(UUID raidGroupId, PageRequest pageRequest);
public List<RaidLayout> findAllByRaidGroupIdIn(Iterable<UUID> raidGroupIds);
public List<RaidLayout> findAllByRaidGroupIdIn(Iterable<UUID> raidGroupIds, PageRequest pageRequest);
public List<RaidLayout> findAllByRaidGroupIdAndRaidLayoutNameContainingIgnoreCase(UUID raidGroupId, String searchTerm, PageRequest pageRequest);
public long countByRaidGroupId(UUID raidGroupId);
public long countByRaidGroupIdAndRaidLayoutNameContainingIgnoreCase(UUID raidGroupId, String searchTerm);
}

View File

@@ -0,0 +1,9 @@
package com.mattrixwv.raidbuilder.repository.raid_layout;
import org.springframework.stereotype.Repository;
@Repository
public class RaidLayoutRepositoryImpl implements RaidLayoutCustomRepository{
}

View File

@@ -0,0 +1,5 @@
package com.mattrixwv.raidbuilder.repository.raid_layout_class_group_xref;
public interface RaidLayoutClassGroupXrefCustomRepository{
}

View File

@@ -0,0 +1,14 @@
package com.mattrixwv.raidbuilder.repository.raid_layout_class_group_xref;
import java.util.UUID;
import org.springframework.data.jpa.repository.JpaRepository;
import com.mattrixwv.raidbuilder.entity.RaidLayoutClassGroupXref;
public interface RaidLayoutClassGroupXrefRepository extends RaidLayoutClassGroupXrefCustomRepository, JpaRepository<RaidLayoutClassGroupXref, UUID>{
public void deleteAllByRaidLayoutId(UUID raidLayoutId);
public void deleteAllByRaidLayoutIdIn(Iterable<UUID> raidLayoutIds);
}

View File

@@ -0,0 +1,9 @@
package com.mattrixwv.raidbuilder.repository.raid_layout_class_group_xref;
import org.springframework.stereotype.Repository;
@Repository
public class RaidLayoutClassGroupXrefRepositoryImpl implements RaidLayoutClassGroupXrefCustomRepository{
}

View File

@@ -70,6 +70,10 @@ public class ClassGroupService{
return classGroupRepository.findByClassGroupIdAndRaidGroupId(classGroupId, raidGroupId);
}
public List<ClassGroup> getClassGroupsByRaidLayoutId(UUID raidLayoutId){
return classGroupRepository.findAllByRaidLayoutId(raidLayoutId);
}
public List<ClassGroup> getClassGroupsByRaidGroupId(UUID raidGroupId, int page, int pageSize){
return classGroupRepository.findAllByRaidGroupId(raidGroupId, PageRequest.of(page, pageSize, Sort.by("classGroupName").ascending()));
}

View File

@@ -0,0 +1,93 @@
package com.mattrixwv.raidbuilder.service;
import java.util.List;
import java.util.UUID;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.mattrixwv.raidbuilder.entity.RaidLayout;
import com.mattrixwv.raidbuilder.entity.RaidLayoutClassGroupXref;
import com.mattrixwv.raidbuilder.repository.raid_layout.RaidLayoutRepository;
import com.mattrixwv.raidbuilder.repository.raid_layout_class_group_xref.RaidLayoutClassGroupXrefRepository;
import lombok.RequiredArgsConstructor;
@Service
@Transactional(rollbackFor = Exception.class)
@RequiredArgsConstructor
public class RaidLayoutService{
private final RaidLayoutRepository raidLayoutRepository;
private final RaidLayoutClassGroupXrefRepository rlcgXrefRepository;
//Write
public RaidLayout createRaidLayout(RaidLayout raidLayout, Iterable<RaidLayoutClassGroupXref> xrefs){
raidLayout = raidLayoutRepository.save(raidLayout);
final UUID raidLayoutId = raidLayout.getRaidLayoutId();
xrefs.forEach(xref -> xref.setRaidLayoutId(raidLayoutId));
rlcgXrefRepository.saveAll(xrefs);
return raidLayout;
}
public RaidLayout updateRaidLayout(RaidLayout raidLayout, Iterable<RaidLayoutClassGroupXref> xrefs){
raidLayout = raidLayoutRepository.save(raidLayout);
final UUID raidLayoutId = raidLayout.getRaidLayoutId();
xrefs.forEach(xref -> xref.setRaidLayoutId(raidLayoutId));
rlcgXrefRepository.deleteAllByRaidLayoutId(raidLayoutId);
rlcgXrefRepository.saveAll(xrefs);
return raidLayout;
}
public void deleteRaidLayout(UUID raidLayoutId, UUID raidGroupId){
rlcgXrefRepository.deleteAllByRaidLayoutId(raidLayoutId);
raidLayoutRepository.deleteByRaidLayoutIdAndRaidGroupId(raidLayoutId, raidGroupId);
}
public void deleteByRaidGroupId(UUID raidGroupId){
List<RaidLayout> raidLayouts = raidLayoutRepository.findAllByRaidGroupId(raidGroupId);
rlcgXrefRepository.deleteAllByRaidLayoutIdIn(raidLayouts.stream().map(RaidLayout::getRaidLayoutId).toList());
raidLayoutRepository.deleteAllByRaidGroupId(raidGroupId);
}
public void deleteByRaidGroupIds(Iterable<UUID> raidGroupIds){
List<RaidLayout> raidLayouts = raidLayoutRepository.findAllByRaidGroupIdIn(raidGroupIds);
rlcgXrefRepository.deleteAllByRaidLayoutIdIn(raidLayouts.stream().map(RaidLayout::getRaidLayoutId).toList());
raidLayoutRepository.deleteAllByRaidGroupIdIn(raidGroupIds);
}
//Read
public RaidLayout getRaidLayout(UUID raidLayoutId, UUID raidGroupId){
return raidLayoutRepository.findByRaidLayoutIdAndRaidGroupId(raidLayoutId, raidGroupId);
}
public List<RaidLayout> getRaidLayoutsByRaidGroupId(UUID raidGroupId, int page, int pageSize){
return raidLayoutRepository.findAllByRaidGroupId(raidGroupId, PageRequest.of(page, pageSize, Sort.by("raidLayoutName").ascending()));
}
public List<RaidLayout> getRaidLayoutsByRaidGroupId(UUID raidGroupId, int page, int pageSize, String searchTerm){
return raidLayoutRepository.findAllByRaidGroupIdAndRaidLayoutNameContainingIgnoreCase(raidGroupId, searchTerm, PageRequest.of(page, pageSize, Sort.by("raidLayoutName").ascending()));
}
public long getRaidLayoutCountByRaidGroupId(UUID raidGroupId){
return raidLayoutRepository.countByRaidGroupId(raidGroupId);
}
public long getRaidLayoutCountByRaidGroupId(UUID raidGroupId, String searchTerm){
return raidLayoutRepository.countByRaidGroupIdAndRaidLayoutNameContainingIgnoreCase(raidGroupId, searchTerm);
}
}