Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ public ResponseEntity<ActivityLogDto> getActivityLogById(@PathVariable Long acti
@GetMapping("/ticket/{supportTicketId}")
public ResponseEntity<List<ActivityLogDto>> getActivityLogsBySupportTicketId(
@PathVariable Long supportTicketId,
@RequestParam(defaultValue = "asc") String sortDirection
@RequestParam(defaultValue = "desc") String sortDirection
Comment thread
VonAdamo marked this conversation as resolved.
) {
return ResponseEntity.ok(
activityLogService.getActivityLogsBySupportTicketId(supportTicketId, sortDirection)
Expand All @@ -61,4 +61,4 @@ public ResponseEntity<List<ActivityLogDto>> getActivityLogsByUserId(
activityLogService.getActivityLogsByUserId(userId, sortDirection)
);
}
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package org.group1.projectbackend.controller;

import java.nio.charset.StandardCharsets;
import java.security.Principal;
import java.util.List;
import org.group1.projectbackend.dto.document.DocumentDownloadResponse;
import org.group1.projectbackend.dto.document.DocumentResponse;
Expand Down Expand Up @@ -57,8 +58,11 @@ public ResponseEntity<Resource> downloadDocument(@PathVariable Long documentId)
}

@DeleteMapping("/documents/{documentId}")
public ResponseEntity<Void> deleteDocument(@PathVariable Long documentId) {
documentService.deleteDocument(documentId);
public ResponseEntity<Void> deleteDocument(
Principal principal,
@PathVariable Long documentId
) {
documentService.deleteDocument(principal.getName(), documentId);
return ResponseEntity.noContent().build();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,11 @@ public ResponseEntity<TicketResponse> getTicketById(@PathVariable Long id) {

@PutMapping("/{id}/status")
public ResponseEntity<TicketResponse> updateTicketStatus(
Principal principal,
@PathVariable Long id,
@Valid @RequestBody UpdateTicketStatusRequest request
) {
TicketResponse updatedTicket = supportTicketService.updateStatus(id, request);
TicketResponse updatedTicket = supportTicketService.updateStatus(principal.getName(), id, request);
return ResponseEntity.ok(updatedTicket);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
package org.group1.projectbackend.controller.web;

import java.time.LocalDate;
import java.util.Arrays;
import java.util.List;
import org.group1.projectbackend.dto.activitylog.ActivityLogDto;
import org.group1.projectbackend.entity.enums.ActivityType;
import org.group1.projectbackend.service.ActivityLogService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;

@Controller
public class ActivityLogViewController {

private final ActivityLogService activityLogService;

public ActivityLogViewController(ActivityLogService activityLogService) {
this.activityLogService = activityLogService;
}

@GetMapping("/activitylogs/view")
public String listActivityLogs(
@RequestParam(required = false) ActivityType type,
@RequestParam(required = false) String username,
@RequestParam(required = false) String ticket,
@RequestParam(required = false) LocalDate date,
Model model
) {
String normalizedUsername = normalizeFilterValue(username);
String normalizedTicket = normalizeFilterValue(ticket);

List<ActivityLogDto> activityLogs = activityLogService.getAllActivityLogs().stream()
.sorted((left, right) -> right.getCreatedAt().compareTo(left.getCreatedAt()))
Comment thread
VonAdamo marked this conversation as resolved.
.filter(activityLog -> type == null || activityLog.getActivityType() == type)
.filter(activityLog -> normalizedUsername == null || containsIgnoreCase(activityLog.getUsername(), normalizedUsername))
.filter(activityLog -> normalizedTicket == null
|| containsIgnoreCase(activityLog.getTicketTitle(), normalizedTicket)
|| matchesTicketId(activityLog, normalizedTicket))
.filter(activityLog -> date == null
|| (activityLog.getCreatedAt() != null && activityLog.getCreatedAt().toLocalDate().isEqual(date)))
.toList();

model.addAttribute("activityLogs", activityLogs);
model.addAttribute("activityTypes", Arrays.asList(ActivityType.values()));
model.addAttribute("selectedType", type);
model.addAttribute("selectedUsername", username);
model.addAttribute("selectedTicket", ticket);
model.addAttribute("selectedDate", date);

return "activitylogs/list";
}

private String normalizeFilterValue(String value) {
if (value == null || value.isBlank()) {
return null;
}

return value.trim();
}

private boolean containsIgnoreCase(String source, String expected) {
return source != null && source.toLowerCase().contains(expected.toLowerCase());
}

private boolean matchesTicketId(ActivityLogDto activityLog, String expected) {
return activityLog.getSupportTicketId() != null
&& String.valueOf(activityLog.getSupportTicketId()).contains(expected);
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package org.group1.projectbackend.controller.web;

import java.security.Principal;
import org.group1.projectbackend.service.DocumentService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
Expand All @@ -26,10 +27,11 @@ public String listDocuments(Model model) {
@PostMapping("/documents/{documentId}/delete")
public String deleteDocument(
@PathVariable Long documentId,
Principal principal,
RedirectAttributes redirectAttributes
) {
try {
documentService.deleteDocument(documentId);
documentService.deleteDocument(principal.getName(), documentId);
redirectAttributes.addFlashAttribute("documentSuccess", "Dokumentet togs bort.");
} catch (RuntimeException ex) {
redirectAttributes.addFlashAttribute("documentError", "Dokumentet kunde inte tas bort.");
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
import org.group1.projectbackend.entity.enums.TicketStatus;
import org.group1.projectbackend.exception.ResourceNotFoundException;
import org.group1.projectbackend.repository.UserRepository;
import org.group1.projectbackend.service.ActivityLogService;
import org.group1.projectbackend.service.CommentService;
import org.group1.projectbackend.service.DocumentService;
import org.group1.projectbackend.service.SupportTicketService;
Expand All @@ -29,17 +30,20 @@
public class TicketViewController {

private final SupportTicketService supportTicketService;
private final ActivityLogService activityLogService;
private final CommentService commentService;
private final DocumentService documentService;
private final UserRepository userRepository;

public TicketViewController(
SupportTicketService supportTicketService,
ActivityLogService activityLogService,
CommentService commentService,
DocumentService documentService,
UserRepository userRepository
) {
this.supportTicketService = supportTicketService;
this.activityLogService = activityLogService;
this.commentService = commentService;
this.documentService = documentService;
this.userRepository = userRepository;
Expand All @@ -54,6 +58,7 @@ public String listTickets(Model model) {
@GetMapping("/tickets/{id}")
public String showTicket(@PathVariable Long id, Model model) {
model.addAttribute("ticket", supportTicketService.getTicketById(id));
model.addAttribute("activityLogs", activityLogService.getActivityLogsBySupportTicketId(id, "desc"));
model.addAttribute("comments", commentService.getCommentsBySupportTicketId(id, "asc"));
model.addAttribute("documents", documentService.listDocumentsForTicket(id));
model.addAttribute("statuses", TicketStatus.values());
Expand Down Expand Up @@ -128,10 +133,11 @@ public String uploadDocument(
public String deleteDocument(
@PathVariable Long ticketId,
@PathVariable Long documentId,
Principal principal,
RedirectAttributes redirectAttributes
) {
try {
documentService.deleteDocument(documentId);
documentService.deleteDocument(principal.getName(), documentId);
redirectAttributes.addFlashAttribute("documentSuccess", "Dokumentet togs bort.");
} catch (RuntimeException ex) {
redirectAttributes.addFlashAttribute("documentError", "Dokumentet kunde inte tas bort.");
Expand All @@ -143,9 +149,10 @@ public String deleteDocument(
@PostMapping("/tickets/{id}/status")
public String updateTicketStatus(
@PathVariable Long id,
@RequestParam TicketStatus status
@RequestParam TicketStatus status,
Principal principal
) {
supportTicketService.updateStatus(id, new UpdateTicketStatusRequest(status));
supportTicketService.updateStatus(principal.getName(), id, new UpdateTicketStatusRequest(status));

return "redirect:/tickets/" + id;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,12 @@
public class ActivityLogDto {

private Long id;
private ActivityType activityType;
private String description;
private Long userId;
private String username;
private Long supportTicketId;
private String ticketTitle;
private ActivityType activityType;
private String description;
private LocalDateTime createdAt;

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,12 @@ public ActivityLogDto toDto(ActivityLog activityLog) {

return new ActivityLogDto(
activityLog.getId(),
activityLog.getActivityType(),
activityLog.getDescription(),
activityLog.getUser() != null ? activityLog.getUser().getId() : null,
activityLog.getUser() != null ? activityLog.getUser().getUsername() : null,
activityLog.getSupportTicket() != null ? activityLog.getSupportTicket().getId() : null,
activityLog.getSupportTicket() != null ? activityLog.getSupportTicket().getTitle() : null,
activityLog.getActivityType(),
activityLog.getDescription(),
activityLog.getCreatedAt()
);
}
Expand All @@ -39,4 +41,4 @@ public ActivityLog toEntity(CreateActivityLogDto dto, User user, SupportTicket s
null
);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import org.group1.projectbackend.entity.ActivityLog;
import org.group1.projectbackend.entity.SupportTicket;
import org.group1.projectbackend.entity.User;
import org.group1.projectbackend.exception.ResourceNotFoundException;
import org.group1.projectbackend.mapper.ActivityLogMapper;
import org.group1.projectbackend.repository.ActivityLogRepository;
import org.group1.projectbackend.repository.SupportTicketRepository;
Expand Down Expand Up @@ -35,12 +36,12 @@ public ActivityLogService(ActivityLogRepository activityLogRepository,

public ActivityLogDto createActivityLog(CreateActivityLogDto dto) {
User user = userRepository.findById(dto.getUserId())
.orElseThrow(() -> new RuntimeException("User not found with id: " + dto.getUserId()));
.orElseThrow(() -> new ResourceNotFoundException("User not found with id: " + dto.getUserId()));

SupportTicket supportTicket = null;
if (dto.getSupportTicketId() != null) {
supportTicket = supportTicketRepository.findById(dto.getSupportTicketId())
.orElseThrow(() -> new RuntimeException("Support ticket not found with id: " + dto.getSupportTicketId()));
.orElseThrow(() -> new ResourceNotFoundException("Support ticket not found with id: " + dto.getSupportTicketId()));
}

ActivityLog activityLog = activityLogMapper.toEntity(dto, user, supportTicket);
Expand All @@ -58,12 +59,16 @@ public List<ActivityLogDto> getAllActivityLogs() {

public ActivityLogDto getActivityLogById(Long id) {
ActivityLog activityLog = activityLogRepository.findById(id)
.orElseThrow(() -> new RuntimeException("Activity log not found with id: " + id));
.orElseThrow(() -> new ResourceNotFoundException("Activity log not found with id: " + id));

return activityLogMapper.toDto(activityLog);
}

public List<ActivityLogDto> getActivityLogsBySupportTicketId(Long supportTicketId, String sortDirection) {
if (!supportTicketRepository.existsById(supportTicketId)) {
throw new ResourceNotFoundException("Support ticket not found with id: " + supportTicketId);
}

Sort sort = "desc".equalsIgnoreCase(sortDirection)
? Sort.by("createdAt").descending()
: Sort.by("createdAt").ascending();
Expand All @@ -84,4 +89,4 @@ public List<ActivityLogDto> getActivityLogsByUserId(Long userId, String sortDire
.map(activityLogMapper::toDto)
.toList();
}
}
}
40 changes: 22 additions & 18 deletions src/main/java/org/group1/projectbackend/service/CommentService.java
Original file line number Diff line number Diff line change
Expand Up @@ -45,17 +45,12 @@ public CommentDto createComment(CreateCommentDto dto) {
Comment comment = commentMapper.toEntity(dto, user, ticket);
Comment savedComment = commentRepository.save(comment);

try {
CreateActivityLogDto logDto = new CreateActivityLogDto(
ActivityType.COMMENT_CREATED,
"Comment created for ticket id: " + ticket.getId(),
user.getId(),
ticket.getId()
);
activityLogService.createActivityLog(logDto);
} catch (Exception e) {
System.err.println("Failed to create activity log: " + e.getMessage());
}
logActivitySafely(
ActivityType.COMMENT_CREATED,
"Comment created for ticket id: " + ticket.getId(),
user.getId(),
ticket.getId()
);

return commentMapper.toDto(savedComment);
}
Expand Down Expand Up @@ -87,14 +82,12 @@ public void deleteComment(Long id) {
.orElseThrow(() -> new RuntimeException("Comment not found with id: " + id));
commentRepository.delete(comment);

CreateActivityLogDto logDto = new CreateActivityLogDto(
logActivitySafely(
ActivityType.COMMENT_DELETED,
"Comment deleted with id: " + comment.getId(),
comment.getUser().getId(),
comment.getTicket().getId()
);

activityLogService.createActivityLog(logDto);
}

// Update comment
Expand All @@ -105,16 +98,27 @@ public CommentDto updateComment(Long id, UpdateCommentDto dto) {
commentMapper.updateEntity(dto, existingComment);
Comment updatedComment = commentRepository.save(existingComment);

CreateActivityLogDto logDto = new CreateActivityLogDto(
logActivitySafely(
ActivityType.COMMENT_UPDATED,
"Comment updated with id: " + existingComment.getId(),
existingComment.getUser().getId(),
existingComment.getTicket().getId()
);

activityLogService.createActivityLog(logDto);

return commentMapper.toDto(updatedComment);

}
}

private void logActivitySafely(ActivityType activityType, String description, Long userId, Long ticketId) {
try {
activityLogService.createActivityLog(new CreateActivityLogDto(
activityType,
description,
userId,
ticketId
));
} catch (RuntimeException ex) {
System.err.println("Failed to create activity log: " + ex.getMessage());
}
}
Comment thread
VonAdamo marked this conversation as resolved.
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,5 +15,5 @@ public interface DocumentService {

DocumentDownloadResponse downloadDocument(Long documentId);

void deleteDocument(Long documentId);
void deleteDocument(String username, Long documentId);
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ public interface SupportTicketService {

TicketResponse getTicketById(Long ticketId);

TicketResponse updateStatus(Long ticketId, UpdateTicketStatusRequest request);
TicketResponse updateStatus(String username, Long ticketId, UpdateTicketStatusRequest request);

List<TicketResponse> getAllTickets();

Expand Down
Loading