Fix refund flow
This commit is contained in:
@@ -372,6 +372,11 @@ public class SaleController {
|
||||
private void openRefundDialog() {
|
||||
try {
|
||||
SaleLineItem selectedSale = tvSales.getSelectionModel().getSelectedItem();
|
||||
if (selectedSale != null && selectedSale.isRefund()) {
|
||||
showError("Refund", "Select an original sale, not an existing refund.");
|
||||
return;
|
||||
}
|
||||
|
||||
FXMLLoader loader = new FXMLLoader(getClass().getResource(
|
||||
"/org/example/petshopdesktop/dialogviews/refund-dialog-view.fxml"));
|
||||
Stage dialog = new Stage();
|
||||
|
||||
@@ -86,6 +86,8 @@ public class RefundDialogController {
|
||||
private Button btnCancel;
|
||||
|
||||
private SaleResponse currentSale;
|
||||
private final List<SaleItemResponse> baseOriginalItems = new ArrayList<>();
|
||||
private final ObservableList<SaleItemResponse> originalItems = FXCollections.observableArrayList();
|
||||
private final ObservableList<RefundItem> refundItems = FXCollections.observableArrayList();
|
||||
private final NumberFormat currency = NumberFormat.getCurrencyInstance(Locale.CANADA);
|
||||
|
||||
@@ -102,6 +104,7 @@ public class RefundDialogController {
|
||||
colOriginalQuantity.setCellValueFactory(new PropertyValueFactory<>("quantity"));
|
||||
colOriginalUnitPrice.setCellValueFactory(new PropertyValueFactory<>("unitPrice"));
|
||||
colOriginalTotal.setCellValueFactory(new PropertyValueFactory<>("lineTotal"));
|
||||
tvOriginalItems.setItems(originalItems);
|
||||
tvOriginalItems.getSelectionModel().setSelectionMode(SelectionMode.SINGLE);
|
||||
|
||||
colRefundProduct.setCellValueFactory(new PropertyValueFactory<>("productName"));
|
||||
@@ -143,6 +146,11 @@ public class RefundDialogController {
|
||||
try {
|
||||
List<SaleResponse> allSales = SaleApi.getInstance().listSales(0, 1000, null);
|
||||
currentSale = SaleApi.getInstance().getSale(saleId);
|
||||
if (Boolean.TRUE.equals(currentSale.getIsRefund())) {
|
||||
clearLoadedSale();
|
||||
showError("Load Sale", "Select an original sale, not a refund record.");
|
||||
return;
|
||||
}
|
||||
List<SaleResponse> previousRefunds = allSales.stream()
|
||||
.filter(s -> Boolean.TRUE.equals(s.getIsRefund()) && saleId.equals(s.getOriginalSaleId()))
|
||||
.collect(Collectors.toList());
|
||||
@@ -161,10 +169,13 @@ public class RefundDialogController {
|
||||
return;
|
||||
}
|
||||
|
||||
tvOriginalItems.setItems(FXCollections.observableArrayList(refundableItems));
|
||||
baseOriginalItems.clear();
|
||||
baseOriginalItems.addAll(copySaleItems(refundableItems));
|
||||
originalItems.setAll(copySaleItems(refundableItems));
|
||||
cbPaymentMethod.getSelectionModel().select(currentSale.getPaymentMethod());
|
||||
|
||||
refundItems.clear();
|
||||
updateOriginalItemAvailability();
|
||||
updateRefundTotal();
|
||||
|
||||
} catch (Exception e) {
|
||||
@@ -215,12 +226,8 @@ public class RefundDialogController {
|
||||
return;
|
||||
}
|
||||
|
||||
refundItems.add(new RefundItem(
|
||||
selected.getProdId().intValue(),
|
||||
selected.getProductName(),
|
||||
quantity,
|
||||
selected.getUnitPrice().doubleValue()
|
||||
));
|
||||
addOrMergeRefundItem(selected, quantity);
|
||||
updateOriginalItemAvailability();
|
||||
updateRefundTotal();
|
||||
|
||||
} catch (NumberFormatException e) {
|
||||
@@ -234,6 +241,7 @@ public class RefundDialogController {
|
||||
RefundItem selected = tvRefundItems.getSelectionModel().getSelectedItem();
|
||||
if (selected != null) {
|
||||
refundItems.remove(selected);
|
||||
updateOriginalItemAvailability();
|
||||
updateRefundTotal();
|
||||
}
|
||||
}
|
||||
@@ -309,6 +317,83 @@ public class RefundDialogController {
|
||||
closeDialog();
|
||||
}
|
||||
|
||||
private void clearLoadedSale() {
|
||||
currentSale = null;
|
||||
lblSaleInfo.setText("");
|
||||
baseOriginalItems.clear();
|
||||
originalItems.clear();
|
||||
refundItems.clear();
|
||||
updateRefundTotal();
|
||||
}
|
||||
|
||||
private void addOrMergeRefundItem(SaleItemResponse selected, int quantity) {
|
||||
for (int i = 0; i < refundItems.size(); i++) {
|
||||
RefundItem existing = refundItems.get(i);
|
||||
if (existing.getProdId() == selected.getProdId().intValue()) {
|
||||
refundItems.set(i, new RefundItem(
|
||||
existing.getProdId(),
|
||||
existing.getProductName(),
|
||||
existing.getQuantity() + quantity,
|
||||
existing.getUnitPrice()
|
||||
));
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
refundItems.add(new RefundItem(
|
||||
selected.getProdId().intValue(),
|
||||
selected.getProductName(),
|
||||
quantity,
|
||||
selected.getUnitPrice().doubleValue()
|
||||
));
|
||||
}
|
||||
|
||||
private void updateOriginalItemAvailability() {
|
||||
if (currentSale == null) {
|
||||
baseOriginalItems.clear();
|
||||
originalItems.clear();
|
||||
return;
|
||||
}
|
||||
|
||||
Map<Long, Integer> pendingRefunds = new HashMap<>();
|
||||
for (RefundItem refundItem : refundItems) {
|
||||
pendingRefunds.merge((long) refundItem.getProdId(), refundItem.getQuantity(), Integer::sum);
|
||||
}
|
||||
|
||||
List<SaleItemResponse> refreshedItems = new ArrayList<>();
|
||||
for (SaleItemResponse originalItem : baseOriginalItems) {
|
||||
SaleItemResponse refreshedItem = copySaleItem(originalItem);
|
||||
int pending = pendingRefunds.getOrDefault(refreshedItem.getProdId(), 0);
|
||||
refreshedItem.setQuantity(Math.max(0, refreshedItem.getQuantity() - pending));
|
||||
if (refreshedItem.getQuantity() > 0) {
|
||||
refreshedItems.add(refreshedItem);
|
||||
}
|
||||
}
|
||||
|
||||
originalItems.setAll(refreshedItems);
|
||||
tvOriginalItems.getSelectionModel().clearSelection();
|
||||
tvOriginalItems.refresh();
|
||||
tvRefundItems.refresh();
|
||||
}
|
||||
|
||||
private List<SaleItemResponse> copySaleItems(List<SaleItemResponse> items) {
|
||||
List<SaleItemResponse> copies = new ArrayList<>();
|
||||
for (SaleItemResponse item : items) {
|
||||
copies.add(copySaleItem(item));
|
||||
}
|
||||
return copies;
|
||||
}
|
||||
|
||||
private SaleItemResponse copySaleItem(SaleItemResponse source) {
|
||||
SaleItemResponse copy = new SaleItemResponse();
|
||||
copy.setSaleItemId(source.getSaleItemId());
|
||||
copy.setProdId(source.getProdId());
|
||||
copy.setProductName(source.getProductName());
|
||||
copy.setQuantity(source.getQuantity());
|
||||
copy.setUnitPrice(source.getUnitPrice());
|
||||
return copy;
|
||||
}
|
||||
|
||||
private void updateRefundTotal() {
|
||||
double total = refundItems.stream().mapToDouble(RefundItem::getTotal).sum();
|
||||
lblRefundTotal.setText(currency.format(total));
|
||||
|
||||
Reference in New Issue
Block a user