Weiter an den Locations gearbeitet
Some checks failed
Host-Based Deploy (Java 21 Fix) / build-and-run (push) Has been cancelled
Some checks failed
Host-Based Deploy (Java 21 Fix) / build-and-run (push) Has been cancelled
This commit is contained in:
176
src/main/java/de/oaa/xxx/location/LocationAdminController.java
Normal file
176
src/main/java/de/oaa/xxx/location/LocationAdminController.java
Normal file
@@ -0,0 +1,176 @@
|
||||
package de.oaa.xxx.location;
|
||||
|
||||
import de.oaa.xxx.location.entity.LocationAdminEntity;
|
||||
import de.oaa.xxx.location.repository.LocationAdminRepository;
|
||||
import de.oaa.xxx.location.repository.LocationRepository;
|
||||
import de.oaa.xxx.user.UserRepository;
|
||||
import de.oaa.xxx.user.UserService;
|
||||
import jakarta.transaction.Transactional;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import java.security.Principal;
|
||||
import java.time.LocalDateTime;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/locations/{locationId}/admins")
|
||||
public class LocationAdminController {
|
||||
|
||||
record AdminDto(UUID userId, String name, String profilePicture, boolean isOwner) {}
|
||||
record AddAdminRequest(UUID userId) {}
|
||||
record TransferOwnerRequest(UUID userId) {}
|
||||
|
||||
private final LocationRepository locationRepo;
|
||||
private final LocationAdminRepository adminRepo;
|
||||
private final UserRepository userRepo;
|
||||
private final UserService userService;
|
||||
|
||||
public LocationAdminController(LocationRepository locationRepo,
|
||||
LocationAdminRepository adminRepo,
|
||||
UserRepository userRepo,
|
||||
UserService userService) {
|
||||
this.locationRepo = locationRepo;
|
||||
this.adminRepo = adminRepo;
|
||||
this.userRepo = userRepo;
|
||||
this.userService = userService;
|
||||
}
|
||||
|
||||
// ── Hilfsmethoden ────────────────────────────────────────────────────────
|
||||
|
||||
private boolean isAdmin(UUID locationId, UUID userId, de.oaa.xxx.location.entity.LocationEntity loc) {
|
||||
return loc.getOwnerId().equals(userId)
|
||||
|| adminRepo.existsByLocationIdAndUserId(locationId, userId);
|
||||
}
|
||||
|
||||
private AdminDto toDto(UUID userId, de.oaa.xxx.location.entity.LocationEntity loc) {
|
||||
return userRepo.findById(userId).map(u -> new AdminDto(
|
||||
u.getUserId(), u.getName(), u.getProfilePicture(),
|
||||
u.getUserId().equals(loc.getOwnerId())))
|
||||
.orElse(null);
|
||||
}
|
||||
|
||||
// ── Admins auflisten ─────────────────────────────────────────────────────
|
||||
|
||||
@GetMapping
|
||||
public ResponseEntity<List<AdminDto>> list(
|
||||
@PathVariable UUID locationId,
|
||||
Principal principal) {
|
||||
|
||||
userService.requireUser(principal);
|
||||
var locOpt = locationRepo.findById(locationId);
|
||||
if (locOpt.isEmpty()) return ResponseEntity.notFound().build();
|
||||
var loc = locOpt.get();
|
||||
|
||||
// Inhaber ist immer erster Eintrag
|
||||
List<AdminDto> admins = new java.util.ArrayList<>();
|
||||
userRepo.findById(loc.getOwnerId()).ifPresent(owner ->
|
||||
admins.add(new AdminDto(owner.getUserId(), owner.getName(), owner.getProfilePicture(), true)));
|
||||
|
||||
adminRepo.findByLocationId(locationId).stream()
|
||||
.filter(a -> !a.getUserId().equals(loc.getOwnerId())) // Inhaber nicht doppelt
|
||||
.map(a -> toDto(a.getUserId(), loc))
|
||||
.filter(java.util.Objects::nonNull)
|
||||
.forEach(admins::add);
|
||||
|
||||
return ResponseEntity.ok(admins);
|
||||
}
|
||||
|
||||
// ── Admin hinzufügen ──────────────────────────────────────────────────────
|
||||
|
||||
@PostMapping
|
||||
public ResponseEntity<AdminDto> add(
|
||||
@PathVariable UUID locationId,
|
||||
@RequestBody AddAdminRequest req,
|
||||
Principal principal) {
|
||||
|
||||
UUID myId = userService.requireUser(principal).getUserId();
|
||||
var locOpt = locationRepo.findById(locationId);
|
||||
if (locOpt.isEmpty()) return ResponseEntity.notFound().build();
|
||||
var loc = locOpt.get();
|
||||
|
||||
if (!isAdmin(locationId, myId, loc)) return ResponseEntity.status(403).build();
|
||||
if (req.userId() == null || !userRepo.existsById(req.userId()))
|
||||
return ResponseEntity.badRequest().build();
|
||||
|
||||
// Inhaber muss nicht eingetragen werden
|
||||
if (req.userId().equals(loc.getOwnerId()))
|
||||
return ResponseEntity.badRequest().build();
|
||||
|
||||
// Bereits Admin?
|
||||
if (adminRepo.existsByLocationIdAndUserId(locationId, req.userId()))
|
||||
return ResponseEntity.status(409).build();
|
||||
|
||||
LocationAdminEntity entity = new LocationAdminEntity();
|
||||
entity.setAdminId(UUID.randomUUID());
|
||||
entity.setLocationId(locationId);
|
||||
entity.setUserId(req.userId());
|
||||
entity.setAddedAt(LocalDateTime.now());
|
||||
adminRepo.save(entity);
|
||||
|
||||
return ResponseEntity.status(201).body(toDto(req.userId(), loc));
|
||||
}
|
||||
|
||||
// ── Admin entfernen ───────────────────────────────────────────────────────
|
||||
|
||||
@Transactional
|
||||
@DeleteMapping("/{userId}")
|
||||
public ResponseEntity<Void> remove(
|
||||
@PathVariable UUID locationId,
|
||||
@PathVariable UUID userId,
|
||||
Principal principal) {
|
||||
|
||||
UUID myId = userService.requireUser(principal).getUserId();
|
||||
var locOpt = locationRepo.findById(locationId);
|
||||
if (locOpt.isEmpty()) return ResponseEntity.notFound().build();
|
||||
var loc = locOpt.get();
|
||||
|
||||
if (!isAdmin(locationId, myId, loc)) return ResponseEntity.status(403).build();
|
||||
|
||||
// Inhaber darf nicht entfernt werden
|
||||
if (userId.equals(loc.getOwnerId())) return ResponseEntity.status(403).build();
|
||||
|
||||
adminRepo.deleteByLocationIdAndUserId(locationId, userId);
|
||||
return ResponseEntity.noContent().build();
|
||||
}
|
||||
|
||||
// ── Inhaberwechsel ────────────────────────────────────────────────────────
|
||||
|
||||
@Transactional
|
||||
@PutMapping("/transfer-owner")
|
||||
public ResponseEntity<Map<String, Object>> transferOwner(
|
||||
@PathVariable UUID locationId,
|
||||
@RequestBody TransferOwnerRequest req,
|
||||
Principal principal) {
|
||||
|
||||
UUID myId = userService.requireUser(principal).getUserId();
|
||||
var locOpt = locationRepo.findById(locationId);
|
||||
if (locOpt.isEmpty()) return ResponseEntity.notFound().build();
|
||||
var loc = locOpt.get();
|
||||
|
||||
// Nur der aktuelle Inhaber darf übertragen
|
||||
if (!loc.getOwnerId().equals(myId)) return ResponseEntity.status(403).build();
|
||||
if (req.userId() == null || !userRepo.existsById(req.userId()))
|
||||
return ResponseEntity.badRequest().build();
|
||||
if (req.userId().equals(myId)) return ResponseEntity.badRequest().build();
|
||||
|
||||
// Neuer Inhaber als Admin eintragen (falls noch nicht), alter Inhaber wird normaler Admin
|
||||
if (!adminRepo.existsByLocationIdAndUserId(locationId, myId)) {
|
||||
LocationAdminEntity a = new LocationAdminEntity();
|
||||
a.setAdminId(UUID.randomUUID());
|
||||
a.setLocationId(locationId);
|
||||
a.setUserId(myId);
|
||||
a.setAddedAt(LocalDateTime.now());
|
||||
adminRepo.save(a);
|
||||
}
|
||||
// Neuen Inhaber aus Admin-Liste entfernen (er ist jetzt Owner)
|
||||
adminRepo.deleteByLocationIdAndUserId(locationId, req.userId());
|
||||
|
||||
loc.setOwnerId(req.userId());
|
||||
locationRepo.save(loc);
|
||||
|
||||
return ResponseEntity.ok(Map.of("newOwnerId", req.userId()));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user