| Line 752... |
Line 752... |
| 752 |
// Admins must be assigned to the ticket OR be CRM user OR be in the escalation chain
|
752 |
// Admins must be assigned to the ticket OR be CRM user OR be in the escalation chain
|
| 753 |
AuthUser currentAuthUser = authRepository.selectByEmailOrMobile(loginDetails.getEmailId());
|
753 |
AuthUser currentAuthUser = authRepository.selectByEmailOrMobile(loginDetails.getEmailId());
|
| 754 |
boolean isCrmUser = positionRepository.hasCategory(currentAuthUser.getId(), ProfitMandiConstants.TICKET_CATEGORY_CRM);
|
754 |
boolean isCrmUser = positionRepository.hasCategory(currentAuthUser.getId(), ProfitMandiConstants.TICKET_CATEGORY_CRM);
|
| 755 |
|
755 |
|
| 756 |
if (!isCrmUser) {
|
756 |
if (!isCrmUser) {
|
| - |
|
757 |
// Assigned = user was ever the assignee or manager on this ticket (any level).
|
| - |
|
758 |
// The old l1..l5AuthUser fallback check was fully subsumed by this since it
|
| 757 |
// Check if user is assigned or in escalation chain
|
759 |
// includes every past TicketAssigned row.
|
| 758 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
760 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
| 759 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
761 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
| 760 |
boolean isInEscalationChain = ticket.getL1AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 761 |
ticket.getL2AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 762 |
ticket.getL3AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 763 |
ticket.getL4AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 764 |
ticket.getL5AuthUser() == currentAuthUser.getId();
|
- |
|
| 765 |
|
762 |
|
| 766 |
// Check if user is related to this partner (RBM, ASM, BM etc.)
|
763 |
// Check if user is related to this partner (RBM, ASM, BM etc.)
|
| 767 |
boolean isRelatedToPartner = false;
|
764 |
boolean isRelatedToPartner = false;
|
| 768 |
if (!isAssigned && !isInEscalationChain) {
|
765 |
if (!isAssigned) {
|
| 769 |
List<AuthUser> relatedUsers = csService.getAuthUserIdByPartnerId(ticket.getFofoId());
|
766 |
List<AuthUser> relatedUsers = csService.getAuthUserIdByPartnerId(ticket.getFofoId());
|
| 770 |
isRelatedToPartner = relatedUsers.stream()
|
767 |
isRelatedToPartner = relatedUsers.stream()
|
| 771 |
.anyMatch(au -> au.getId() == currentAuthUser.getId());
|
768 |
.anyMatch(au -> au.getId() == currentAuthUser.getId());
|
| 772 |
if (!isRelatedToPartner) {
|
769 |
if (!isRelatedToPartner) {
|
| 773 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to view this ticket");
|
770 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to view this ticket");
|
| 774 |
}
|
771 |
}
|
| 775 |
}
|
772 |
}
|
| 776 |
|
773 |
|
| 777 |
// User can view but cannot take action if only related to partner (not assigned/escalation)
|
774 |
// User can view but cannot take action if only related to partner (not assigned)
|
| 778 |
model.addAttribute("canTakeAction", isAssigned || isInEscalationChain);
|
775 |
model.addAttribute("canTakeAction", isAssigned);
|
| 779 |
}
|
776 |
}
|
| 780 |
}
|
777 |
}
|
| 781 |
|
778 |
|
| 782 |
List<Activity> allactivities = activityRepository.selectAll(ticketId);
|
779 |
List<Activity> allactivities = activityRepository.selectAll(ticketId);
|
| 783 |
|
780 |
|
| Line 871... |
Line 868... |
| 871 |
boolean isCrmUser = positionRepository.hasCategory(currentAuthUser.getId(), ProfitMandiConstants.TICKET_CATEGORY_CRM);
|
868 |
boolean isCrmUser = positionRepository.hasCategory(currentAuthUser.getId(), ProfitMandiConstants.TICKET_CATEGORY_CRM);
|
| 872 |
|
869 |
|
| 873 |
if (!isCrmUser) {
|
870 |
if (!isCrmUser) {
|
| 874 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
871 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
| 875 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
872 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
| 876 |
boolean isInEscalationChain = ticket.getL1AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 877 |
ticket.getL2AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 878 |
ticket.getL3AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 879 |
ticket.getL4AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 880 |
ticket.getL5AuthUser() == currentAuthUser.getId();
|
- |
|
| 881 |
|
873 |
|
| 882 |
if (!isAssigned && !isInEscalationChain) {
|
874 |
if (!isAssigned) {
|
| 883 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to add activity to this ticket");
|
875 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to add activity to this ticket");
|
| 884 |
}
|
876 |
}
|
| 885 |
}
|
877 |
}
|
| 886 |
}
|
878 |
}
|
| 887 |
List<TicketAssigned> ticketAssignedList = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
879 |
List<TicketAssigned> ticketAssignedList = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
| Line 1016... |
Line 1008... |
| 1016 |
}
|
1008 |
}
|
| 1017 |
}
|
1009 |
}
|
| 1018 |
|
1010 |
|
| 1019 |
authUserListMap = csService.getAssignedAuthList(tickets);
|
1011 |
authUserListMap = csService.getAssignedAuthList(tickets);
|
| 1020 |
|
1012 |
|
| 1021 |
// Find which tickets are assigned to or escalated to this user (can take action)
|
1013 |
// Find which tickets are assigned to or escalated to this user (can take action).
|
| - |
|
1014 |
// TicketAssigned history covers every past assignee + manager pair, which fully
|
| - |
|
1015 |
// subsumes the previous l1..l5AuthUser fallback loop.
|
| 1022 |
Set<Integer> actionableTicketIds = new HashSet<>();
|
1016 |
Set<Integer> actionableTicketIds = new HashSet<>();
|
| 1023 |
if (tickets.size() > 0) {
|
1017 |
if (tickets.size() > 0) {
|
| 1024 |
List<TicketAssigned> allAssignments = ticketAssignedRepository.selectByTicketIds(
|
1018 |
List<TicketAssigned> allAssignments = ticketAssignedRepository.selectByTicketIds(
|
| 1025 |
tickets.stream().map(Ticket::getId).collect(Collectors.toList()));
|
1019 |
tickets.stream().map(Ticket::getId).collect(Collectors.toList()));
|
| 1026 |
for (TicketAssigned ta : allAssignments) {
|
1020 |
for (TicketAssigned ta : allAssignments) {
|
| 1027 |
if (ta.getAssineeId() == authUser.getId() || ta.getManagerId() == authUser.getId()) {
|
1021 |
if (ta.getAssineeId() == authUser.getId() || ta.getManagerId() == authUser.getId()) {
|
| 1028 |
actionableTicketIds.add(ta.getTicketId());
|
1022 |
actionableTicketIds.add(ta.getTicketId());
|
| 1029 |
}
|
1023 |
}
|
| 1030 |
}
|
1024 |
}
|
| 1031 |
// Also check escalation chain
|
- |
|
| 1032 |
for (Ticket t : tickets) {
|
- |
|
| 1033 |
if (t.getL1AuthUser() == authUser.getId() || t.getL2AuthUser() == authUser.getId()
|
- |
|
| 1034 |
|| t.getL3AuthUser() == authUser.getId() || t.getL4AuthUser() == authUser.getId()
|
- |
|
| 1035 |
|| t.getL5AuthUser() == authUser.getId()) {
|
- |
|
| 1036 |
actionableTicketIds.add(t.getId());
|
- |
|
| 1037 |
}
|
- |
|
| 1038 |
}
|
- |
|
| 1039 |
Map<Integer, CustomRetailer> fofoIdsAndCustomRetailer = csService.getPartnerByFofoIds(tickets);
|
1025 |
Map<Integer, CustomRetailer> fofoIdsAndCustomRetailer = csService.getPartnerByFofoIds(tickets);
|
| 1040 |
model.addAttribute("fofoIdsAndCustomRetailer", fofoIdsAndCustomRetailer);
|
1026 |
model.addAttribute("fofoIdsAndCustomRetailer", fofoIdsAndCustomRetailer);
|
| 1041 |
}
|
1027 |
}
|
| 1042 |
model.addAttribute("actionableTicketIds", actionableTicketIds);
|
1028 |
model.addAttribute("actionableTicketIds", actionableTicketIds);
|
| 1043 |
|
1029 |
|
| Line 1282... |
Line 1268... |
| 1282 |
|
1268 |
|
| 1283 |
// Check permissions
|
1269 |
// Check permissions
|
| 1284 |
boolean hasPositionInCategory = positionRepository.hasCategory(currentAuthUser.getId(), ticketCategoryId);
|
1270 |
boolean hasPositionInCategory = positionRepository.hasCategory(currentAuthUser.getId(), ticketCategoryId);
|
| 1285 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
1271 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
| 1286 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
1272 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
| 1287 |
boolean isInEscalationChain = ticket.getL1AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1288 |
ticket.getL2AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1289 |
ticket.getL3AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1290 |
ticket.getL4AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1291 |
ticket.getL5AuthUser() == currentAuthUser.getId();
|
- |
|
| 1292 |
|
1273 |
|
| 1293 |
boolean canEdit = (isCrmUser && isVisibleSubCategory)
|
1274 |
boolean canEdit = (isCrmUser && isVisibleSubCategory)
|
| 1294 |
|| hasPositionInCategory
|
1275 |
|| hasPositionInCategory
|
| 1295 |
|| isAssigned
|
1276 |
|| isAssigned;
|
| 1296 |
|| isInEscalationChain;
|
- |
|
| 1297 |
|
1277 |
|
| 1298 |
if (!canEdit) {
|
1278 |
if (!canEdit) {
|
| 1299 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to edit this ticket");
|
1279 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to edit this ticket");
|
| 1300 |
}
|
1280 |
}
|
| 1301 |
|
1281 |
|
| Line 1380... |
Line 1360... |
| 1380 |
boolean isVisibleSubCategory = ticketSubCategory.isVisibility();
|
1360 |
boolean isVisibleSubCategory = ticketSubCategory.isVisibility();
|
| 1381 |
|
1361 |
|
| 1382 |
// Check if user has position in ticket's category
|
1362 |
// Check if user has position in ticket's category
|
| 1383 |
boolean hasPositionInCategory = positionRepository.hasCategory(currentAuthUser.getId(), ticketCategoryId);
|
1363 |
boolean hasPositionInCategory = positionRepository.hasCategory(currentAuthUser.getId(), ticketCategoryId);
|
| 1384 |
|
1364 |
|
| 1385 |
// Check if assigned or in escalation chain
|
1365 |
// Check if assigned (assignee or manager at any level in history)
|
| 1386 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
1366 |
List<TicketAssigned> assignments = ticketAssignedRepository.selectByTicketIds(Arrays.asList(ticketId));
|
| 1387 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
1367 |
boolean isAssigned = assignments.stream().anyMatch(ta -> ta.getAssineeId() == currentAuthUser.getId() || ta.getManagerId() == currentAuthUser.getId());
|
| 1388 |
boolean isInEscalationChain = ticket.getL1AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1389 |
ticket.getL2AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1390 |
ticket.getL3AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1391 |
ticket.getL4AuthUser() == currentAuthUser.getId() ||
|
- |
|
| 1392 |
ticket.getL5AuthUser() == currentAuthUser.getId();
|
- |
|
| 1393 |
|
1368 |
|
| 1394 |
// Permission rules:
|
1369 |
// Permission rules:
|
| 1395 |
// 1. CRM user AND ticket has visible subcategory, OR
|
1370 |
// 1. CRM user AND ticket has visible subcategory, OR
|
| 1396 |
// 2. Has position in ticket's category (can edit even invisible), OR
|
1371 |
// 2. Has position in ticket's category (can edit even invisible), OR
|
| 1397 |
// 3. Is assigned to ticket, OR
|
1372 |
// 3. Is assigned to ticket at any past level (assignee or manager)
|
| 1398 |
// 4. Is in escalation chain
|
- |
|
| 1399 |
boolean canEdit = (isCrmUser && isVisibleSubCategory)
|
1373 |
boolean canEdit = (isCrmUser && isVisibleSubCategory)
|
| 1400 |
|| hasPositionInCategory
|
1374 |
|| hasPositionInCategory
|
| 1401 |
|| isAssigned
|
1375 |
|| isAssigned;
|
| 1402 |
|| isInEscalationChain;
|
- |
|
| 1403 |
|
1376 |
|
| 1404 |
if (!canEdit) {
|
1377 |
if (!canEdit) {
|
| 1405 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to edit this ticket");
|
1378 |
throw new ProfitMandiBusinessException("Ticket", ticketId, "You do not have permission to edit this ticket");
|
| 1406 |
}
|
1379 |
}
|
| 1407 |
|
1380 |
|
| Line 1518... |
Line 1491... |
| 1518 |
activity.setTicketId(ticketId);
|
1491 |
activity.setTicketId(ticketId);
|
| 1519 |
activity.setType(ActivityType.COMMUNICATION_IN);
|
1492 |
activity.setType(ActivityType.COMMUNICATION_IN);
|
| 1520 |
activity.setCreateTimestamp(LocalDateTime.now());
|
1493 |
activity.setCreateTimestamp(LocalDateTime.now());
|
| 1521 |
} else {
|
1494 |
} else {
|
| 1522 |
String message = String.format(INTERNAL_REOPEN_MAIL, ticketId, retailerService.getFofoRetailer(loginDetails.getFofoId()).getBusinessName());
|
1495 |
String message = String.format(INTERNAL_REOPEN_MAIL, ticketId, retailerService.getFofoRetailer(loginDetails.getFofoId()).getBusinessName());
|
| - |
|
1496 |
// Reopen mail goes to the current assignee with the current manager on CC.
|
| - |
|
1497 |
// Previously fanned out to all l1..l5 slots which were pre-populated at creation.
|
| - |
|
1498 |
String to = ticket.getCurrentAssigneeId() > 0
|
| 1523 |
String to = authRepository.selectById(ticket.getL1AuthUser()).getEmailId();
|
1499 |
? authRepository.selectById(ticket.getCurrentAssigneeId()).getEmailId()
|
| - |
|
1500 |
: null;
|
| - |
|
1501 |
String[] ccTo = ticket.getCurrentManagerId() > 0
|
| 1524 |
String[] ccTo = authRepository.selectByIds(Arrays.asList(ticket.getL2AuthUser(), ticket.getL3AuthUser(), ticket.getL4AuthUser(), ticket.getL5AuthUser())).stream().map(x -> x.getEmailId()).toArray(String[]::new);
|
1502 |
? new String[]{authRepository.selectById(ticket.getCurrentManagerId()).getEmailId()}
|
| - |
|
1503 |
: new String[0];
|
| 1525 |
ticket.setLastActivity(lastActivity);
|
1504 |
ticket.setLastActivity(lastActivity);
|
| 1526 |
ticket.setUpdateTimestamp(LocalDateTime.now());
|
1505 |
ticket.setUpdateTimestamp(LocalDateTime.now());
|
| 1527 |
ticketAssignedRepository.deleteByTicketId(ticketId);
|
1506 |
ticketAssignedRepository.deleteByTicketId(ticketId);
|
| 1528 |
TicketAssigned ticketAssigned = new TicketAssigned();
|
1507 |
TicketAssigned ticketAssigned = new TicketAssigned();
|
| 1529 |
ticketAssigned.setAssineeId(ticket.getL1AuthUser());
|
1508 |
ticketAssigned.setAssineeId(ticket.getCurrentAssigneeId());
|
| 1530 |
ticketAssigned.setTicketId(ticketId);
|
1509 |
ticketAssigned.setTicketId(ticketId);
|
| 1531 |
ticketAssignedRepository.persist(ticketAssigned);
|
1510 |
ticketAssignedRepository.persist(ticketAssigned);
|
| 1532 |
activity.setMessage(INTERNAL_REOPEN_ACTIVITY_MESSAGE);
|
1511 |
activity.setMessage(INTERNAL_REOPEN_ACTIVITY_MESSAGE);
|
| 1533 |
activity.setCreatedBy(0);
|
1512 |
activity.setCreatedBy(0);
|
| 1534 |
activity.setTicketId(ticketId);
|
1513 |
activity.setTicketId(ticketId);
|