这是关于JSF + JPA应用程序。
Bill和BillItem是两个实体,与JPA应用程序中的cascadeType = all具有双边OneToMany关系。
当使用单击新Bill时,将创建一个新的Bill对象。然后,用户填写BillItem的属性,如名称和数量,然后单击“添加到帐单”按钮,以便将BillItem添加到Bill对象的BillItem列表中。使用链接到bill.billItems的数据表更新用户界面。
在帐单中添加一个或多个billItem后,用户单击持有帐单对象的结算按钮。
问题是无法从列表中删除billItem。始终删除第一个项目。如何从列表中获取所需的billItem?
条例实体守则
@Entity
public class Bill implements Serializable {
@OneToMany(mappedBy = "bill", cascade = CascadeType.ALL, fetch = FetchType.EAGER)
List<BillItem> billItems = new ArrayList<>();
...
..
}
BillItem实体的代码
@Entity
public class BillItem implements Serializable {
@ManyToOne
Bill bill;
....
...
@Override
public boolean equals(Object object) {
if (!(object instanceof BillItem)) {
return false;
}
BillItem other = (BillItem) object;
if ((this.id == null && other.id != null) || (this.id != null && !this.id.equals(other.id))) {
return false;
}
return true;
}
}
JSF Managed Bean的代码
@Named
@SessionScoped
public class SaleController implements Serializable {
private BilledBill bill;
BillItem billItem;
public void removeItem(){
if(removingItem==null){
UtilityController.addErrorMessage("Select one to remove");
return;
}
getBill().getBillItems().remove(removingItem);
}
public String newSaleBill() {
fillAvailableStocks();
listBillsToSettle();
clearBill();
clearBillItem();
printPreview = false;
bill = null;
return "sale";
}
public void settle() {
....
saveBill();
UtilityController.addSuccessMessage("Successfully Billed");
}
public void addItem() {
......
getBill().getBillItems().add(billItem);
calTotal();
clearBillItem();
}
public void saveBill() {
bill.setBillType(BillType.SaleToCustomer);
getBill().setInstitution(getSessionController().getInstitution());
getBill().setDepartment(getSessionController().getDepartment());
getBill().setStaff(getSessionController().getLoggedUser().getStaff());
getBill().setDeptId(getBillNumberBean().departmentBillNumberGenerator(getSessionController().getDepartment(), BillType.SaleToCustomer, BillNumberSuffix.SB));
getBill().setInsId(getBillNumberBean().institutionBillNumberGenerator(getSessionController().getInstitution(), BillType.SaleToCustomer, BillNumberSuffix.SB));
getBill().setRepId(getBillNumberBean().institutionBillNumberGenerator(getSessionController().getLoggedUser().getStaff(), BillType.SaleToCustomer, BillNumberSuffix.SB));
getBill().setToInstitution(getSessionController().getInstitution());
getBill().setToDepartment(getSessionController().getDepartment());
getBill().setCreatedAt(new Date());
getBill().setBillDate(Calendar.getInstance().getTime());
getBill().setCreater(getSessionController().getLoggedUser());
getBillFacade().create(getBill());
}
public BilledBill getBill() {
if (bill == null) {
bill = new BilledBill();
getBillFacade().create(bill);
}
return bill;
}
public BillItem getBillItem() {
if (billItem == null) {
billItem = new BillItem();
}
return billItem;
}
public void setBillItem(BillItem BillItem) {
this.billItem = BillItem;
}
public BillItem getRemovingItem() {
return removingItem;
}
public void setRemovingItem(BillItem removingItem) {
this.removingItem = removingItem;
}
}
JSF页面
<h:panelGrid columns="5">
<h:outputLabel value="Select Item"/>
<h:outputLabel value="Qty (kg)"/>
<h:outputLabel value="Rate"/>
<h:outputLabel value="Value"/>
<h:outputLabel value=""/>
<p:selectOneMenu id="acItem" converter="stockCon" value="#{saleController.billItem.stock}" var="vt" >
<f:selectItems value="#{saleController.availableStock}" var="ast" itemValue="#{ast}" itemLabel="#{ast.itemBatch.item.name}" ></f:selectItems>
<p:column >
<h:outputLabel value="#{vt.itemBatch.item.name}" ></h:outputLabel>
</p:column>
<p:column >
<h:outputLabel value="#{vt.stock}" ></h:outputLabel>
</p:column>
</p:selectOneMenu>
<p:inputText id="txtQty" value="#{saleController.billItem.qty}" styleClass="normalNoBox" >
<f:ajax event="blur" execute="acItem txtQty " render="" listener="#{saleController.calValueFromRate()}"></f:ajax>
</p:inputText>
<p:inputText id="txtRate" value="#{saleController.billItem.netRate}" styleClass="normalNoBox" >
<f:ajax event="blur" execute="acItem txtQty txtRate" render="lblVal" listener="#{saleController.calValueFromRate()}" ></f:ajax>
</p:inputText>
<h:outputLabel id="lblVal" value="#{saleController.billItem.netValue}" styleClass="normalNoBox" ></h:outputLabel>
<p:commandButton value="Add Item" action="#{saleController.addItem}" ajax="false" />
</h:panelGrid>
<p:panelGrid columns="2">
</p:panelGrid>
</h:panelGrid>
<p:dataTable var="ph" value="#{saleController.bill.billItems}" id="itemList">
<f:facet name="header">
<h:outputLabel value="Sale Items" ></h:outputLabel>
</f:facet>
<p:column headerText="Item Name" style="width:30%">
<h:outputLabel id="item" value="#{ph.item.name}" >
</h:outputLabel>
</p:column>
<p:column headerText="Qty (kg)" style="width:20%">
<h:outputLabel id="qty" value="#{ph.qty}" >
</h:outputLabel>
</p:column>
<p:column headerText="Rate" style="width:20%">
<h:outputLabel id="itemRate" value="#{ph.grossRate}" >
</h:outputLabel>
</p:column>
<p:column headerText="Value" style="width:20%">
<h:outputLabel id="itemVal" value="#{ph.grossValue}" >
</h:outputLabel>
</p:column>
<p:column headerText="Remove" style="width:20%">
<h:commandButton value="Remove" action="#{saleController.removeItem()}" >
<f:setPropertyActionListener target="#{saleController.removingItem}" value="#{ph}" ></f:setPropertyActionListener>
</h:commandButton>
</p:column>
</p:dataTable>
</p:panel>