use of uk.ac.bbsrc.tgac.miso.core.data.Boxable in project miso-lims by miso-lims.
the class DefaultBoxService method updateBoxableLocation.
@Override
public void updateBoxableLocation(Boxable boxable) throws IOException {
BoxableId boxableId = new BoxableId(boxable.getEntityType(), boxable.getId());
Boxable managedOriginal = boxStore.getBoxable(boxableId);
if (boxable.getBox() == null && managedOriginal.getBox() == null) {
return;
}
if ((boxable.getBox() != null && managedOriginal.getBox() != null && boxable.getBox().getId() == managedOriginal.getBox().getId() && boxable.getBoxPosition().equals(managedOriginal.getBoxPosition()))) {
// Note: for new items, boxable.box.boxPosition[boxable.boxPosition] may not match boxable.boxPosition because it doesn't (and we
// don't want it to) cascade update. boxable.boxPosition stays as it is because Hibernate won't overwrite the changes you've made to
// the object with the current session. boxable.box should be a refreshed object with the correct, persisted boxPositions though.
BoxPosition temp = managedOriginal.getBox().getBoxPositions().get(managedOriginal.getBoxPosition());
if (temp != null && temp.getBoxableId().equals(boxableId)) {
return;
}
}
if (managedOriginal.getBox() != null) {
Box box = get(managedOriginal.getBox().getId());
box.getBoxPositions().remove(managedOriginal.getBoxPosition());
addBoxContentsChangeLog(managedOriginal.getBox(), String.format("Removed %s (%s) from %s", managedOriginal.getAlias(), managedOriginal.getName(), managedOriginal.getBoxPosition()));
box.setChangeDetails(authorizationManager.getCurrentUser());
boxStore.save(box);
}
if (boxable.getBox() != null) {
Box managedNew = boxStore.get(boxable.getBox().getId());
addBoxContentsChangeLog(managedNew, String.format("Added %s (%s) to %s", boxable.getAlias(), boxable.getName(), boxable.getBoxPosition()));
managedNew.getBoxPositions().put(boxable.getBoxPosition(), new BoxPosition(managedNew, boxable.getBoxPosition(), boxable.getEntityType(), boxable.getId()));
managedNew.setChangeDetails(authorizationManager.getCurrentUser());
boxStore.save(managedNew);
}
}
use of uk.ac.bbsrc.tgac.miso.core.data.Boxable in project miso-lims by miso-lims.
the class DefaultBoxService method update.
@Override
public long update(Box box) throws IOException {
box.setChangeDetails(authorizationManager.getCurrentUser());
if (box.getStorageLocation() != null) {
box.setStorageLocation(storageLocationService.get(box.getStorageLocation().getId()));
} else {
box.setStorageLocation(null);
}
loadChildEntities(box);
Box managed = boxStore.get(box.getId());
logStorageChange(box, managed);
validateChange(box, managed);
applyChanges(box, managed);
StringBuilder message = new StringBuilder();
// get persisted version of new box contents before change
List<BoxableId> ids = box.getBoxPositions().values().stream().map(BoxPosition::getBoxableId).collect(Collectors.toList());
Map<BoxableId, BoxableView> oldOccupants = boxStore.getBoxableViewsByIdList(ids).stream().collect(Collectors.toMap(view -> new BoxableId(view.getEntityType(), view.getId()), Functions.identity()));
// Process additions/moves
Set<BoxPosition> movedWithinBox = Sets.newHashSet();
List<BoxableView> movedFromOtherBoxes = new ArrayList<>();
for (Map.Entry<String, BoxPosition> entry : box.getBoxPositions().entrySet()) {
BoxPosition managedPos = managed.getBoxPositions().get(entry.getKey());
BoxPosition newPos = entry.getValue();
if (managedPos != null && newPos.getBoxableId().equals(managedPos.getBoxableId())) {
// Unchanged
continue;
}
if (message.length() > 0) {
message.append("\n");
}
BoxableView oldOccupant = oldOccupants.get(newPos.getBoxableId());
if (oldOccupant.getBoxId() != null) {
if (oldOccupant.getBoxId().longValue() == box.getId()) {
// Moved within same box
message.append(String.format("Relocated %s (%s) from %s to %s", oldOccupant.getAlias(), oldOccupant.getName(), oldOccupant.getBoxPosition(), entry.getKey()));
movedWithinBox.add(newPos);
} else {
// Moved from a different box
Box oldBox = get(oldOccupant.getBoxId());
addBoxContentsChangeLog(oldBox, String.format("Removed %s (%s) from %s to %s (%s)", oldOccupant.getAlias(), oldOccupant.getName(), oldOccupant.getBoxPosition(), managed.getAlias(), managed.getName()));
message.append(String.format("Moved %s (%s) from %s (%s) to %s", oldOccupant.getAlias(), oldOccupant.getName(), oldOccupant.getBoxAlias(), oldOccupant.getBoxName(), entry.getKey()));
movedFromOtherBoxes.add(oldOccupant);
}
} else {
message.append(String.format("Added %s (%s) to %s", oldOccupant.getAlias(), oldOccupant.getName(), entry.getKey()));
}
}
// Process removals
List<BoxableId> removedIds = new ArrayList<>();
List<BoxableId> movedWithinBoxIds = movedWithinBox.stream().map(BoxPosition::getBoxableId).collect(Collectors.toList());
for (Map.Entry<String, BoxPosition> entry : managed.getBoxPositions().entrySet()) {
if (box.getBoxPositions().keySet().contains(entry.getKey()) && box.getBoxPositions().get(entry.getKey()).getBoxableId().equals(entry.getValue().getBoxableId())) {
// Already handled. Only checking for removals at this point
continue;
}
removedIds.add(entry.getValue().getBoxableId());
}
List<BoxableView> removed = boxStore.getBoxableViewsByIdList(removedIds);
for (BoxableView v : removed) {
if (!movedWithinBoxIds.contains(new BoxableId(v.getEntityType(), v.getId()))) {
if (message.length() > 0) {
message.append("\n");
}
message.append(String.format("Removed %s (%s) from %s", v.getAlias(), v.getName(), v.getBoxPosition()));
}
}
for (BoxableView v : movedFromOtherBoxes) {
boxStore.removeBoxableFromBox(v);
}
movedWithinBox.forEach(bp -> managed.getBoxPositions().remove(bp.getPosition()));
removed.forEach(boxable -> managed.getBoxPositions().remove(boxable.getBoxPosition()));
if (!movedWithinBox.isEmpty() || !removed.isEmpty()) {
boxStore.save(managed);
}
for (String pos : box.getBoxPositions().keySet()) {
if (!managed.getBoxPositions().containsKey(pos) || !managed.getBoxPositions().get(pos).getBoxableId().equals(box.getBoxPositions().get(pos).getBoxableId())) {
managed.getBoxPositions().put(pos, new BoxPosition(managed, pos, box.getBoxPositions().get(pos).getBoxableId()));
}
}
if (message.length() > 0) {
addBoxContentsChangeLog(managed, message.toString());
}
managed.setChangeDetails(authorizationManager.getCurrentUser());
return boxStore.save(managed);
}
use of uk.ac.bbsrc.tgac.miso.core.data.Boxable in project miso-lims by miso-lims.
the class DefaultTransferService method validateItems.
private <T extends Boxable, U extends TransferItem<T>> void validateItems(Transfer transfer, Transfer beforeChange, Function<Transfer, Set<U>> getItems, List<ValidationError> errors) throws IOException {
Set<U> items = getItems.apply(transfer);
Set<U> beforeChangeItems = beforeChange == null ? null : getItems.apply(beforeChange);
if (items.stream().anyMatch(item -> Boolean.FALSE.equals(item.isQcPassed()) && LimsUtils.isStringEmptyOrNull(item.getQcNote()))) {
errors.add(new ValidationError("items", ERROR_QC_NOTE_REQUIRED));
}
if (beforeChange != null && !authorizationManager.isAdminUser() && transfer.getSenderGroup() != null && !authorizationManager.isGroupMember(transfer.getSenderGroup()) && (items.size() != beforeChangeItems.size() || items.stream().anyMatch(item -> beforeChangeItems.stream().noneMatch(beforeItem -> beforeItem.getItem().getId() == item.getItem().getId())))) {
errors.add(new ValidationError("items", ERROR_UNAUTHORIZED_ITEM_MODIFY));
}
if (!authorizationManager.isAdminUser()) {
if (beforeChange == null) {
if (transfer.getRecipientGroup() != null && !authorizationManager.isGroupMember(transfer.getRecipientGroup())) {
if (items.stream().anyMatch(item -> item.isQcPassed() != null || item.getQcNote() != null)) {
errors.add(new ValidationError("items", ERROR_UNAUTHORIZED_QC));
}
if (items.stream().anyMatch(item -> item.isReceived() != null)) {
errors.add(new ValidationError("items", ERROR_UNAUTHORIZED_RECEIPT));
}
}
} else {
if (!authorizationManager.isGroupMember(transfer.getRecipientGroup()) && items.stream().anyMatch(item -> {
U beforeChangeItem = beforeChangeItems.stream().filter(before -> before.getItem().getId() == item.getItem().getId()).findFirst().orElse(null);
return beforeChangeItem != null && isChanged(item, beforeChangeItem);
})) {
errors.add(new ValidationError("items", "Only administrators and members of the recipient group can mark receipt and QC results"));
}
}
}
if (transfer.isDistribution() && items.stream().anyMatch(item -> !Boolean.TRUE.equals(item.isReceived()))) {
errors.add(new ValidationError("items", ERROR_DISTRIBUTION_NOT_RECEIVED));
}
if (transfer.getSenderLab() != null) {
if (items.stream().map(TransferItem::getItem).anyMatch(item -> item.getTransferViews().stream().anyMatch(itemTransfer -> itemTransfer.isReceipt() && (!transfer.isSaved() || itemTransfer.getId() != transfer.getId())))) {
errors.add(new ValidationError("items", ERROR_MULTIPLE_RECEIPT));
}
} else if (transfer.getRecipient() != null && items.stream().map(TransferItem::getItem).anyMatch(item -> item.getTransferViews().stream().anyMatch(itemTransfer -> itemTransfer.isDistribution() && (!transfer.isSaved() || itemTransfer.getId() != transfer.getId())))) {
errors.add(new ValidationError("items", ERROR_MULTIPLE_DISTRIBUTION));
}
}
Aggregations