私のアプリケーションには、「N」個の製品を見積もりに関連付けることができるという要件があります。画面レイアウトには 2 つの部分があります。上部には見積もり関連の情報を含むフォームがあり、下部には複数の製品を保持するためのものです。下部に iframe を配置することで、この機能を実装しました。商品の追加・削除はボタンクリック(javascript使用)で行います。すべての製品ウィンドウ内に表示されるコンテンツは、同じアクション (ProductLinesAction.java)、JSP (ProductLines.jsp)、およびその他の関連リソースによってレンダリングされます。ここでのポイントは、新しい製品ウィンドウが画面に読み込まれるたびに、その Action クラスの複数のインスタンスが作成されることです。表示するフォームを準備するだけなので、ウィンドウの読み込みに問題はありません。見積もりを保存する間、これらのすべての製品フォームが送信され、私が組み込んだロジックは、1 対 N-1 のアクション インスタンスがフォーム値を VO に配置し、Vector オブジェクトに追加されてセッションに保存されるというものです (他のアクション インスタンスが取得できるようにするため)。セッションから、その上に追加します)。N 番目のアクション インスタンスは、これらすべての製品値をまとめて保存するためのものです。ビジネス ルールの検証も保存の直前に実行されるため、N 番目のアクション インスタンスが使用可能になり、すべての製品ウィンドウにエラーが表示されます。N 番目のアクション インスタンスは、これらすべての製品値をまとめて保存するためのものです。ビジネス ルールの検証も保存の直前に実行されるため、N 番目のアクション インスタンスが使用可能になり、すべての製品ウィンドウにエラーが表示されます。N 番目のアクション インスタンスは、これらすべての製品値をまとめて保存するためのものです。ビジネス ルールの検証も保存の直前に実行されるため、N 番目のアクション インスタンスが使用可能になり、すべての製品ウィンドウにエラーが表示されます。
他のすべてのアクション インスタンスもそのウィンドウに対応するエラーを確実に利用できるようにするために、6 つを超える製品を保存しようとするとうまくいかない wait および notifyAll メカニズムを実装しました。コードを以下に示します。このコードは、製品数が 6 以下 (つまり、最大 6 つのアクション インスタンス) の場合に問題なく機能します。7 番目の製品をロードして保存すると、7 番目のインスタンスはデバッグ モードでまったく表示されず、追跡できません (インスタンスは、フォームの送信時に意図したメソッドに到達しません)。
この問題の原因である、ここで犯された間違いに誰かが光を当てることができますか.
public String submitProducts()
throws Exception {
String resultValue = "";
/* Algorithm: */
// 1. Read the Vector object from Session.
// 2. Check whether the size of the Vector matches the Total Product windows count.
// 3. If yes, call the Save operation and remove the list from session.
// 4. If not, copy the values from current Action instance to VO.
// 5. Add to List object and place in session.
synchronized (productVOsInVector) {
productVOsInVector = getProductVOVectorFromSession();
if (productVOsInVector == null) {
productVOsInVector = new Vector <ProductVO>();
}
log.info("Window Number is " + activeWindowNumber + ". List size is " + productVOsInVector.size());
if (productVOsInVector.size() == (prodWindowCount - 1)) {
productVOsInVector = mapActionToVO(productVOsInVector);
resultValue = saveOperation(productVOsInVector);
if (resultValue.equalsIgnoreCase(SUCCESS)) {
session.put("OperationStatus", SUCCESS);
}
session.remove("productVOMapData");
}
else {
if (quoteSaveStatus) {
quoteSaveStatus = false;
}
session.put("OperationStatus", "");
productVOsInVector = mapActionToVO(productVOsInVector);
session.put("productVOMapData", productVOsInVector);
}
waitForOperationStatus();
}
System.out.println("Came out of sync block");
System.out.println("Action Instance" + activeWindowNumber + " is resuming.");
// Code to display the Error messages
return resultValue;
}
public void waitForOperationStatus() {
String opStatus = getOperationStatusFromSession();
synchronized (productVOsInVector) {
if (!opStatus.equalsIgnoreCase(SUCCESS)) {
try {
System.out.println("Window # " + activeWindowNumber + " Waiting");
productVOsInVector.wait();
}
catch (InterruptedException e) {
e.printStackTrace();
}
opStatus = getOperationStatusFromSession();
}
productVOsInVector.notifyAll();
}
}