DBA Data[Home] [Help]

PACKAGE BODY: APPS.GME_CREATE_BATCH_PVT

Source


1 PACKAGE BODY gme_create_batch_pvt AS
2 /* $Header: GMEVCRBB.pls 120.54.12020000.4 2013/03/21 15:38:47 gmurator ship $ */
3    g_debug               VARCHAR2 (5)
4                                := NVL (fnd_profile.VALUE ('AFLOG_LEVEL'), 99);
5    g_pkg_name   CONSTANT VARCHAR2 (30) := 'GME_CREATE_BATCH_PVT';
6 
7 /***********************************************************/
8 /* Oracle Process Manufacturing Process Execution APIs     */
9 /*                                                         */
10 /* File Name: GMEVCRBB.pls                                 */
11 /* Contents:  Private layer for batch creation API         */
12 /* HISTORY                                                 */
13 /* SivakumarG 05-APR-2006                                  */
14 /*  put some debug messages in edit text copy code         */
15 /*  sunitha bug # 5484529 selecting the sum of the plan    */
16 /*  quantity without converting it to the UOM that the user entered */
17 /*  while creating the batch into l_temp_qty .Convert the  */
18 /*  p_batch_size(user entered product plan quantity        */
19 /*  to the Routing uom and then Compare it with l_temp_qty.*/
20 /*  Kapil M. Bug# 5458674                                  */
21 /*  Changes to Support LCF Batches for GMO                 */
22 /*  Archana Mundhe Bug 5763818 Modified the code to use    */
23 /*  ERES constants that are added to gme_common_pvt instead*/
24 /*  of using the hardcoded ERES event names such as        */
25 /*  'oracle.apps.gme...'                                   */
26 /*  Swapna K Bug#6398619 calls to validate_wip_entity are changed */
27 /*   for the manual doc ordering                             */
28 
29 /* Please use this new format for comments going forward.
30 
31   G. Muratore     12/26/2007  Bug 6665602 Back out fix for 5484529. This fix was
32      incorrect. The select fixed in 5484529 was not correct because it did not convert
33      all product lines to one common uom. Therefore the summation is invalid.
34      Bug 5484529 will ahve to be re-addressed in a different way.
35   Swapna K Bug#6738476 Added parameter,p_batch_header_rec
36     to the procedure call,gme_phantom_pvt.create_phantom
37  10-JAN-2008 Rajesh Patangya Bug # 6752637
38  MTQ Quantity should be calculated based on product in place of just copy from
39  the routing, This is required by PS engine, New Function UPDATE_STEP_MTQ added
40 
41   G. Muratore     07/31/2008  Bug 7265006 Correct fix for 5512352.
42      This fix was incorrect as to where the new condition was used when trying to optimize shortage checking.
43      Moved g_no_phant_short_check to shortage check condition as it was originally intended
44      for shortage checking only. Unfortunately it stopped all the other logic for phantom batches.
45      Now invisible move orders and high level reservations will get created for phantom batches.
46 
47   G. Muratore     08/18/2008  Bug 7284242
48      This fix was to correct the algorithm for deriving the scale factor when creating a batch by
49      'PRODUCT'.  Prior to this fix the code did not treat fixed scale products differently from
50      linear scale products.
51 
52   K. swapna       10/21/2008  Bug 7493614
53      Moved the call to wf_event.raise call to the end of the create_batch
54       procedure as the sample can be created at the end of the batch creation.
55 
56   G. Muratore     18-NOV-2008  Bug 7565054 - Rework of 7284242
57      This fix was to correct the algorithm for deriving the scale factor when creating a batch by
58      'PRODUCT'. When a batch is created from APS, the Quantity being passed is in reference to the
59      primary product line only. Create batch did not treat it the same way if the same item existed in
60      multiple product lines. Added parameter p_sum_all_prod_lines to the procedure create_batch.
61      Parameter values: "A" means sum all the lines i.e. original functionality. "S" means single product summation.
62      The original fix dealt with fixed scale type only which we now know was not the real issue. The
63      New paramater will allow APS a way to tell this code to consider only the primary product line.
64      In the future this could be extended to the forms since the parameter now exists.
65 
66   G. Muratore     25-NOV-2008  Bug 7578476 - Some Rework of 4917631 also done.
67      This fix was to correct the algorithm for deriving the original_primary_qty. The user reported
68      that it was not considering scrap_factor. That in fact was an issue but also it was not calculated
69      properly if the dtl uom was not the primary, in some cases. Changed the code to correct all areas where
70      original_primary_qty is derived. Note: Removed some redundant cursors and code. Also, made use of
71      l_item_masters table array properly to get the correct conversions.
72 
73   G. Muratore     05-FEB-2009  Bug 7830838
74      Use the same value of fixed_process_loss_applied from the parent batch so that FPL
75      gets properly applied, or not applied, to the phantom batch based on user settings.
76      Also includes fix for Bug 7656415. This rounds the plan_qty to make sure it adheres to 5 decimal places.
77 
78   G. Muratore     09-FEB-2009  Bug 8226667
79      Changed select from inline calculation to using variables and making sure that
80      denominator cannot be zero. Procedure: update_step_mtq
81 
82   G. Muratore     26-FEB-2009  Bug 7710435
83      Changed call to gme_material_details_dbl.update_row which now accepts a p_called_by parameter. This allows
84      us to disregard the timestamp used for record locking. It is not required to lock records, during batch create,
85      which are not committed to the database yet. Sometimes, the timestamp in the database record did not match
86      the one in the memory table and therefore updates were failing. Also refetch the material records after the
87      last call to update_row to update the memory tables. PROCEDURE: create_batch.
88 
89   G. Muratore     09-SEP-2010  Bug 10086349
90      Use precision of 4 instead of 5 to make comparison against batch size requested.
91      This is necessary because of potential precision loss.
92 
93   G. Muratore     21-DEC-2010  Bug 10379034 - REWORK OF 10086349
94      Change the comparison against batch size requested so we do not rely on potential rounding issues.
95 
96   G. Muratore     24-JAN-2011  Bug 10624995
97      Rearrange logic as to handle integer scale items for non scaled batches during batch creation.
98 
99   G. Muratore     04-OCT-2011  Bug 12909216 - TWEEK OF 10379034
100      Avoid divide by zero error when qty is zero. This will allow zero phantom batches to be created.
101 
102   A. Mishra       09-DEC-2011  Bug 13256866 -
103      Adding the who columns for every update statement.
104 
105   G. Muratore     09-DEC-2011  Bug 11815699
106      Check to make sure the item is not inactive for process execution based on item status code.
107 
108   G. Muratore     28-FEB-2012  Bug 13785754
109      Changed logic to try 3 times if necessary to get a unique batch number for auto doc numbering.
110      This change was needed for customers firing off creation of many batches by many users. Periodically
111      there was a key constraint issue on the wip entities table.
112 
113   G. Muratore     20-MAR-2012  Bug 13811289
114      Make sure all items returned are valid for the specific organization.
115 
116   G. Muratore     23-MAR-2012  Bug 13785754/13815190
117      Changed logic to try 20 times if necessary to get a unique batch number for auto doc numbering.
118 
119   QZENG           12-Mar-2013  Bug 16457668
120      No need to check batch no for verified in bulk validation when used from batch open interface
121 
122   G. Muratore     21-MAR-2013  Bug 16474091
123      Changed change precision from 5 to 32 for totals that are used in deriving routing scale factor.
124 ************************************************************************************************************  */
125 
126 /************************************************************
127 *                                                           *
128 * CONSTRUCT_BATCH_HEADER                                    *
129 *                                                           *
130 ************************************************************/
131    FUNCTION construct_batch_header (
132       p_batch_header_rec   IN              gme_batch_header%ROWTYPE
133      ,x_batch_header_rec   OUT NOCOPY      gme_batch_header%ROWTYPE)
134       RETURN BOOLEAN
135    IS
136       l_count               NUMBER;
137       l_api_name   CONSTANT VARCHAR2 (30) := 'CONSTRUCT_BATCH_HEADER';
138    BEGIN
139       IF g_debug <= gme_debug.g_log_procedure THEN
140          gme_debug.put_line ('Entering api ' || g_pkg_name || '.'
141                              || l_api_name);
142       END IF;
143 
144       /* Create defaults for mandatory columns that have not been specified */
145       l_count := gme_common_pvt.g_error_count;
146       x_batch_header_rec := p_batch_header_rec;
147 
148       IF x_batch_header_rec.organization_id IS NULL THEN
149          fnd_message.set_name ('INV', 'INV_INT_ORGCODE');
150          fnd_msg_pub.ADD;
151       END IF;
152 
153       x_batch_header_rec.prod_id := NVL (x_batch_header_rec.prod_id, 0);
154       x_batch_header_rec.prod_sequence :=
155                                      NVL (x_batch_header_rec.prod_sequence, 0);
156       x_batch_header_rec.plan_start_date :=
157           NVL (x_batch_header_rec.plan_start_date, gme_common_pvt.g_timestamp);
158       x_batch_header_rec.plan_cmplt_date :=
159           NVL (x_batch_header_rec.plan_cmplt_date, gme_common_pvt.g_timestamp);
160       x_batch_header_rec.due_date :=
161                  NVL (x_batch_header_rec.due_date, gme_common_pvt.g_timestamp);
162       x_batch_header_rec.batch_status := gme_common_pvt.G_BATCH_PENDING;
163       x_batch_header_rec.priority_value :=
164                                     NVL (x_batch_header_rec.priority_value, 0);
165       x_batch_header_rec.priority_code :=
166                                      NVL (x_batch_header_rec.priority_code, 0);
167       x_batch_header_rec.print_count := 0;
168       x_batch_header_rec.batch_close_date := NULL;
169       x_batch_header_rec.actual_cost_ind := 'N';
170       x_batch_header_rec.gl_posted_ind := 0;
171       x_batch_header_rec.delete_mark := 0;
172       x_batch_header_rec.automatic_step_calculation := 1;
173 
174       IF l_count <> gme_common_pvt.g_error_count THEN
175          RETURN FALSE;
176       ELSE
177          RETURN TRUE;
178       END IF;
179    EXCEPTION
180       WHEN OTHERS THEN
181          IF g_debug <= gme_debug.g_log_unexpected THEN
182             gme_debug.put_line (   'When others exception in '
183                                 || g_pkg_name
184                                 || '.'
185                                 || l_api_name
186                                 || ' Error is '
187                                 || SQLERRM);
188          END IF;
189 
190          fnd_msg_pub.add_exc_msg (g_pkg_name, l_api_name);
191          RETURN FALSE;
192    END construct_batch_header;
193 
194    PROCEDURE validate_wip_entity (p_organization_id  IN   NUMBER,
195                                   p_batch_no         IN   VARCHAR2,
196                                   x_return_status    OUT NOCOPY VARCHAR2) IS
197       l_api_name    CONSTANT VARCHAR2 (30) := 'VALIDATE_WIP_ENTITY';
198       l_temp        NUMBER;
199       duplicate_wip_entity EXCEPTION;
200       CURSOR Cur_wip_entity IS
201         SELECT 1
202         FROM   DUAL
203         WHERE  EXISTS (SELECT 1
204                        FROM   wip_entities
205                        WHERE  organization_id = p_organization_id
206                               AND wip_entity_name = p_batch_no);
207    BEGIN
208      x_return_status := fnd_api.g_ret_sts_success;
209      OPEN Cur_wip_entity;
210      FETCH Cur_wip_entity INTO l_temp;
211      IF (Cur_wip_entity%FOUND) THEN
212         CLOSE Cur_wip_entity;
213         RAISE duplicate_wip_entity;
214      END IF;
215      CLOSE Cur_wip_entity;
216    EXCEPTION
217       WHEN duplicate_wip_entity THEN
218         x_return_status := fnd_api.g_ret_sts_error;
219         gme_common_pvt.log_message('GME_WIP_ENTITY_EXISTS');
220       WHEN OTHERS THEN
221          IF g_debug <= gme_debug.g_log_unexpected THEN
222             gme_debug.put_line (   'When others exception in '
223                                 || g_pkg_name
224                                 || '.'
225                                 || l_api_name
226                                 || ' Error is '
227                                 || SQLERRM);
228          END IF;
229          fnd_msg_pub.add_exc_msg (g_pkg_name, l_api_name);
230          x_return_status := fnd_api.g_ret_sts_unexp_error;
231    END validate_wip_entity;
232 
233    PROCEDURE create_batch (
234       p_validation_level         IN              NUMBER
235             := gme_common_pvt.g_max_errors
236      ,p_batch_header_rec         IN              gme_batch_header%ROWTYPE
237      ,p_batch_size               IN              NUMBER
238      ,p_batch_size_uom           IN              VARCHAR2
239      ,p_creation_mode            IN              VARCHAR2
240      ,p_ignore_qty_below_cap     IN              VARCHAR2
241             DEFAULT fnd_api.g_true
242      ,p_use_workday_cal          IN              VARCHAR2
243      ,p_contiguity_override      IN              VARCHAR2
244      ,p_is_phantom               IN              VARCHAR2 DEFAULT 'N'
245      ,p_sum_all_prod_lines       IN              VARCHAR2 DEFAULT 'A'
246      ,p_use_least_cost_validity_rule     IN      VARCHAR2 := fnd_api.g_false
247      ,x_batch_header_rec         OUT NOCOPY      gme_batch_header%ROWTYPE
248      ,x_exception_material_tbl   OUT NOCOPY      gme_common_pvt.exceptions_tab
249      ,x_return_status            OUT NOCOPY      VARCHAR2)
250    IS
251       l_in_batch_header              gme_batch_header%ROWTYPE;
252       l_formula_master               fm_form_mst%ROWTYPE;
253       l_formula_material             fm_matl_dtl%ROWTYPE;
254       l_recipe_validity_rule         gmd_recipe_validity_rules%ROWTYPE;
255       l_item_master                  mtl_system_items_kfv%ROWTYPE;
256       l_gme_material_detail          gme_material_details%ROWTYPE;
257       l_text_header                  gme_text_header%ROWTYPE;
258       l_text_string                  gme_text_table.text%TYPE;
259       l_material_details             gme_common_pvt.material_details_tab;
260       p_material_details             gme_common_pvt.material_details_tab;
261       l_in_material_details          gme_common_pvt.material_details_tab;
262       l_material_details_in          gme_material_details%ROWTYPE;
263       l_item_masters                 gme_common_pvt.item_masters_tab;
264       l_text_table                   gme_common_pvt.text_tab;
265       l_recipe                       gmd_recipes%ROWTYPE;
266       l_from_uom                     mtl_units_of_measure.uom_code%TYPE;
267       l_to_uom                       mtl_units_of_measure.uom_code%TYPE;
268       l_prim_item_um                 mtl_units_of_measure.uom_code%TYPE;
269       l_prim_prod_um                 mtl_units_of_measure.uom_code%TYPE;
270       l_contig_period_tbl            gmp_calendar_api.contig_period_tbl;
271       l_api_name            CONSTANT VARCHAR2 (30)          := 'CREATE_BATCH';
272       l_uom                          VARCHAR2 (4);
273       l_return_status                VARCHAR2 (1);
274       l_message_list                 VARCHAR2 (2000);
275       l_production_um                VARCHAR2 (4);
276       l_primaries                    VARCHAR2 (15);
277       l_item_no                      VARCHAR2 (2000);
278       l_prefix                       VARCHAR2 (32);
279       l_enhanced_pi_ind              VARCHAR2 (1);
280       l_dispense_required            VARCHAR2 (1);
281       l_number_of_product_lines      NUMBER;
282       l_number_of_byproduct_lines    NUMBER;
283       l_number_of_ingredient_lines   NUMBER;
284       l_number_of_formula_lines      NUMBER;
285       l_number_of_text_lines         NUMBER;
286       l_text_code                    NUMBER;
287       l_count                        NUMBER                              := 0;
288       l_message_count                NUMBER;
289       l_doc_numbering                NUMBER;
290       l_doc_count                    NUMBER;  -- 13785754
291       l_process_loss                 NUMBER;
292       l_return_code                  NUMBER;
293       l_total_input_qty              NUMBER;
294       l_total_output_qty             NUMBER;
295       l_total_output_qty_b           NUMBER;
296       l_total_output_qty_c           NUMBER;
297       l_production_rule_qty          NUMBER;
298       l_requested_qty                NUMBER;
299       l_temp_qty                     NUMBER;
300       l_temp_line_no                 NUMBER;
301 
302       l_item_id                      NUMBER;
303       l_inv_trans_count              NUMBER;
304       l_rsc_trans_count              NUMBER;
305       l_prim_prod_qty                NUMBER;
306       l_error_count                  NUMBER;
307       l_error_count_after            NUMBER;
308       l_msg_data                     VARCHAR2(2000);
309       l_duration                     NUMBER;
310       l_cal_count                    NUMBER;
311       l_cont_ind                     NUMBER;
312       l_config_id                               NUMBER;
313       l_excp_tbl_ptr                 NUMBER; -- nsinghi bug#5200395
314       l_return                       BOOLEAN;
315       l_no_prod_rule_found           BOOLEAN;
316       l_prim_prod_found              BOOLEAN;
317       l_exception_material_tbl       gme_common_pvt.exceptions_tab;
318       l_trolin_tbl                   inv_move_order_pub.trolin_tbl_type;
319       l_phantom_exc_material_tbl     gme_common_pvt.exceptions_tab; -- nsinghi bug#5200395
320       l_phantom_exc_material_tbl_out gme_common_pvt.exceptions_tab; -- nsinghi bug#5200395
321       l_batch_header_rec             gme_batch_header%ROWTYPE;
322       l_batchstep_rec                gme_batch_steps%ROWTYPE;
323       x_batchstep_rec                gme_batch_steps%ROWTYPE;
324       l_in_material_detail           gme_material_details%ROWTYPE;
325       l_item_substituted             BOOLEAN;
326       l_curr_item_substituted        BOOLEAN;
327       l_ingred_req_date              DATE;
328       material_dtl_fetch_failure     EXCEPTION;
329 
330       --FPBug#4351032
331       l_formula_tbl                  gmdfmval_pub.formula_detail_tbl;
332       l_new_item_rec                 mtl_system_items_kfv%ROWTYPE;
333       --5698727
334       l_in_batch_header1             gme_batch_header%ROWTYPE;
335       l_doc_timestamp                VARCHAR2(50);
336       l_assignment_type              NUMBER;
337       l_document_no                  gme_batch_header.batch_no%TYPE;
338       --5698727
339       invalid_item_substitute        EXCEPTION;
340       l_gme_batch_header GME_BATCH_HEADER%ROWTYPE;
341 
342       -- Bug 10624995
343       l_change_made                 NUMBER;
344       l_scale_rec                   gmd_common_scale.scale_rec;
345       l_scale_rec_out               gmd_common_scale.scale_rec;
346       error_in_integer_scale        EXCEPTION;
347 
348 
349       CURSOR recipe_validity_rule_cursor (v_recipe_validity_rule_id NUMBER)
350       IS
351          SELECT *
352            FROM gmd_recipe_validity_rules
353           WHERE recipe_validity_rule_id = NVL (v_recipe_validity_rule_id, -1);
354 
355       CURSOR recipe_cursor (v_recipe_id NUMBER)
356       IS
357          SELECT *
358            FROM gmd_recipes
359           WHERE recipe_id = v_recipe_id;
360 
361       CURSOR formula_details_cursor (v_recipe_id NUMBER)
362       IS
363          SELECT   a.*
364              FROM fm_matl_dtl a, gmd_recipes_b b
365             WHERE a.formula_id = b.formula_id AND b.recipe_id = v_recipe_id
366          ORDER BY line_no;
367 
368       CURSOR fm_text_tbl_cursor (v_text_code NUMBER)
369       IS
370          SELECT   *
371              FROM fm_text_tbl
372             WHERE text_code = NVL (v_text_code, -1)
373          ORDER BY line_no;
374 
375       -- pawan kumar changed this cursor for bug 4917631
376 
377       -- Bug 11815699 - Add inventory_item_status_code column
378       -- Bug 7578476 - Fetch primary uom code also.
379       CURSOR item_master_cursor (v_inventory_item_id NUMBER, v_org_id NUMBER)
380       IS
381          SELECT inventory_item_id, concatenated_segments,
382                 eng_item_flag, process_execution_enabled_flag,
383                 primary_uom_code, inventory_item_status_code
384            FROM mtl_system_items_kfv
385           WHERE inventory_item_id = v_inventory_item_id
386             AND organization_id = v_org_id;
387 
388       -- Bug 13811289 - Fetch item description..
389       CURSOR item_master_descr_cursor (v_inventory_item_id NUMBER)
390       IS
391          SELECT DISTINCT concatenated_segments
392            FROM mtl_system_items_kfv
393           WHERE inventory_item_id = v_inventory_item_id
394             AND rownum = 1;
395 
396       -- Bug 11815699 - Fetch process execution enabled setting for item ststus.
397       CURSOR item_status_cursor (v_inventory_item_status_code VARCHAR2)
398       IS
399          SELECT NVL(st.attribute_value, 'N')
400            FROM mtl_stat_attrib_values_all_v st
401           WHERE st.inventory_item_status_code = v_inventory_item_status_code
402             AND attribute_name = 'MTL_SYSTEM_ITEMS.PROCESS_EXECUTION_ENABLED_FLAG';
403 
404       l_status_exec_enabled   VARCHAR2(1);
405 
406       -- Bug 7578476 - Remove redundant cursor introduced by 4917631
407 
408 /*
409  --  pawan kumar added this cursor for bug 4917631
410       CURSOR item_master_cursor_sub (v_inventory_item_id NUMBER, v_org_id NUMBER)
411       IS
412          SELECT primary_uom_code, eng_item_flag, process_execution_enabled_flag
413            FROM mtl_system_items_kfv
414           WHERE inventory_item_id = v_inventory_item_id
415             AND organization_id = v_org_id;
416 */
417 
418       CURSOR production_rules_cursor (
419          v_inventory_item_id   NUMBER
420         ,v_org_id              NUMBER)
421       IS
422          SELECT std_lot_size, primary_uom_code
423            FROM mtl_system_items_b
424           WHERE inventory_item_id = v_inventory_item_id
425             AND organization_id = v_org_id;
426 
427       CURSOR cur_get_doc_ord (v_org_id NUMBER, v_batch_type NUMBER)
428       IS
429          SELECT DECODE (v_batch_type
430                        ,10, fpo_doc_numbering
431                        ,batch_doc_numbering) assignment_type
432            FROM gme_parameters
433           WHERE organization_id = v_org_id;
434 
435       CURSOR cur_val_batch (
436          v_org_id       NUMBER
437         ,v_batch_no     VARCHAR2
438         ,v_batch_type   VARCHAR2)
439       IS
440          SELECT 1
441            FROM DUAL
442           WHERE EXISTS (
443                    SELECT 1
444                      FROM gme_batch_header
445                     WHERE batch_no = v_batch_no
446                       AND organization_id = v_org_id
447                       AND batch_type = v_batch_type);
448 
449       CURSOR get_prim_prod (v_batch_id NUMBER, v_inventory_item_id NUMBER)
450       IS
451          SELECT   plan_qty, dtl_um
452              FROM gme_material_details
453             WHERE batch_id = v_batch_id
454               AND inventory_item_id = v_inventory_item_id
455               AND line_type = gme_common_pvt.g_line_type_prod
456          ORDER BY line_no ASC;
457 
458       -- Bug 6665602 Back out 5484529...  Reinstate original cursor.
459       --sunitha bug # 5484529 selecting the sum of the plan quantity without converting
460       --it to the user entered UOM while creating the batch
461       -- Bug 7565054 - Add v_sum_all_prod_lines paramater to cursor query and also Union.
462       CURSOR cur_batch_qty (v_batch_id NUMBER
463              ,v_inventory_item_id NUMBER
464              ,v_sum_all_prod_lines VARCHAR)
465       IS
466          SELECT SUM (inv_convert.inv_um_convert (v_inventory_item_id
467                                                 ,5
468                                                 ,plan_qty
469                                                 ,dtl_um
470                                                 ,p_batch_size_uom
471                                                 ,NULL
472                                                 ,NULL) ), 1 as line_no
473            FROM gme_material_details
474           WHERE batch_id = v_batch_id
475             AND inventory_item_id = v_inventory_item_id
476             AND line_type = gme_common_pvt.g_line_type_prod
477             AND v_sum_all_prod_lines = 'A'
478          UNION
479          SELECT inv_convert.inv_um_convert (v_inventory_item_id
480                                                 ,5
481                                                 ,plan_qty
482                                                 ,dtl_um
483                                                 ,p_batch_size_uom
484                                                 ,NULL
485                                                 ,NULL), line_no
486            FROM gme_material_details
487           WHERE batch_id = v_batch_id
488             AND inventory_item_id = v_inventory_item_id
489             AND line_type = gme_common_pvt.g_line_type_prod
490             AND v_sum_all_prod_lines <> 'A'
491           ORDER BY line_no;
492 
493       /*CURSOR cur_batch_qty (v_batch_id NUMBER, v_inventory_item_id NUMBER)
494       IS
495          SELECT SUM (plan_qty )
496            FROM gme_material_details
497           WHERE batch_id = v_batch_id
498             AND inventory_item_id = v_inventory_item_id
499             AND line_type = gme_common_pvt.g_line_type_prod; */
500 
501       CURSOR cur_item_no (v_inventory_item_id NUMBER, v_org_id NUMBER)
502       IS
503          SELECT concatenated_segments
504            FROM mtl_system_items_kfv
505           WHERE inventory_item_id = v_inventory_item_id
506             AND organization_id = v_org_id;
507 
508       -- nsinghi bug#5674398 Added the Cursor
509       CURSOR c_batchsteps (p_material_detail_id IN NUMBER) IS
510          SELECT b.*
511            FROM gme_batch_step_items a, gme_batch_steps b
512           WHERE a.batchstep_id = b.batchstep_id AND a.material_detail_id = p_material_detail_id;
513 
514       error_count_exceeded           EXCEPTION;
515       expected_error                 EXCEPTION;
516       unexpected_error               EXCEPTION;
517       scaling_failure                EXCEPTION;
518       invalid_header_values          EXCEPTION;
519       invalid_recipe                 EXCEPTION;
520       conversion_failure             EXCEPTION;
521       steps_creation_failure         EXCEPTION;
522       batch_header_fetch_failure     EXCEPTION;
523       date_exceed_validity_rule      EXCEPTION;
524       error_create_phantom           EXCEPTION;
525       validation_failure             EXCEPTION;
526       create_by_product_failure      EXCEPTION;
527       gme_duplicate_batch            EXCEPTION;
528       doc_num_is_not_passed          EXCEPTION;
529       inventory_shortage             EXCEPTION;
530       error_cont_period              EXCEPTION;
531       error_non_contiguious          EXCEPTION;
532       error_truncate_date            EXCEPTION;
533       create_mo_hdr_err              EXCEPTION;
534       create_mo_line_err             EXCEPTION;
535       calc_mtl_req_date_err          EXCEPTION;
536       gmo_instantiate_err            EXCEPTION;
537       wip_entity_err                 EXCEPTION;
538 
539       --FPBug#4395561
540       create_flex_failure            EXCEPTION;
541       Fixed_process_loss_failure     EXCEPTION;
542       -- Rajesh Patangya Bug # 6752637
543       update_step_mtq_failure        EXCEPTION;
544    BEGIN
545       IF g_debug <= gme_debug.g_log_procedure THEN
546          gme_debug.put_line ('Entering api ' || g_pkg_name || '.'
547                              || l_api_name);
548       END IF;
549       x_return_status := fnd_api.g_ret_sts_success;
550       -- Initialize output batch header
551       x_batch_header_rec := p_batch_header_rec;
552 
553       IF (    p_creation_mode <> 'RECIPE'
554           AND NVL (p_batch_size, 0) = 0
555           AND p_is_phantom <> 'Y') THEN
556          gme_common_pvt.log_message ('GME_API_QTY_CANT_BE_ZERO');
557          RAISE expected_error;
558       END IF;
559 
560       IF x_batch_header_rec.batch_type NOT IN (0, 10) THEN
561          gme_common_pvt.log_message ('GME_INVALID_BATCH_TYPE');
562          RAISE expected_error;
563       END IF;
564 
565       OPEN cur_get_doc_ord (x_batch_header_rec.organization_id
566                            ,x_batch_header_rec.batch_type);
567 
568       FETCH cur_get_doc_ord
569        INTO l_doc_numbering;
570 
571       CLOSE cur_get_doc_ord;
572       IF g_debug <= gme_debug.g_log_procedure THEN
573          gme_debug.put_line ('BEfore document numbering check' || g_pkg_name || '.'
574                              || l_api_name);
575       END IF;
576       IF l_doc_numbering = 1 THEN
577          IF x_batch_header_rec.batch_no IS NULL THEN
578             RAISE doc_num_is_not_passed;
579          ELSE
580 	    --added by qzeng no need to check if done in bulk validation
581 	    IF NVL(gme_common_pvt.g_bulk_validation_done, 'N') = 'N' THEN
582               OPEN cur_val_batch (x_batch_header_rec.organization_id
583                                  ,x_batch_header_rec.batch_no
584                                  ,x_batch_header_rec.batch_type);
585 
586               FETCH cur_val_batch
587                INTO l_count;
588 
589               CLOSE cur_val_batch;
590 
591               IF l_count > 0 THEN
592                 RAISE gme_duplicate_batch;
593               END IF;
594 	    END IF;
595          END IF;                     /* x_batch_header_rec.batch_no IS NULL */
596       END IF;                                     /* IF l_doc_numbering = 1 */
597       IF g_debug <= gme_debug.g_log_procedure THEN
598          gme_debug.put_line ('before laboratory check' || g_pkg_name || '.'
599                              || l_api_name);
600       END IF;
601 
602       IF (gme_common_pvt.g_lab_ind = 1 AND gme_common_pvt.g_plant_ind = 1) THEN
603          IF p_batch_header_rec.laboratory_ind = 1 THEN
604             x_batch_header_rec.laboratory_ind := 1;
605             x_batch_header_rec.update_inventory_ind :=
606                                       p_batch_header_rec.update_inventory_ind;
607          ELSE
608             x_batch_header_rec.laboratory_ind := 0;
609             x_batch_header_rec.update_inventory_ind := 'Y';
610          END IF;
611       ELSIF (gme_common_pvt.g_lab_ind = 1) THEN
612          x_batch_header_rec.laboratory_ind := 1;
613          x_batch_header_rec.update_inventory_ind :=
614                                       p_batch_header_rec.update_inventory_ind;
615       ELSIF (gme_common_pvt.g_plant_ind = 1) THEN
616          x_batch_header_rec.laboratory_ind := 0;
617          x_batch_header_rec.update_inventory_ind := 'Y';
618       END IF;
619       IF g_debug <= gme_debug.g_log_procedure THEN
620          gme_debug.put_line ('After laboratory check' || g_pkg_name || '.'
621                              || l_api_name);
622       END IF;
623 
624       --  Validate/fill in batch header columns
625       l_in_batch_header := x_batch_header_rec;
626       l_return :=
627                 construct_batch_header (l_in_batch_header, x_batch_header_rec);
628 
629       IF NOT l_return THEN
630          RAISE invalid_header_values;
631       END IF;
632       IF g_debug <= gme_debug.g_log_procedure THEN
633          gme_debug.put_line ('After contruct batch header' || g_pkg_name || '.'
634                              || l_api_name);
635       END IF;
636 
637       IF g_debug <= gme_debug.g_log_statement THEN
638          gme_debug.put_line (   g_pkg_name
639                              || '.'
640                              || l_api_name
641                              || 'Starting Validity rule processing');
642       END IF;
643 
644       /* If the batch is being created from LCF
645          then there is no pre-defined formula or
646          validity rule */
647       IF p_creation_mode <> 'LCF' THEN
648          -- Validate recipe validity rule
649          OPEN recipe_validity_rule_cursor
650                                   (x_batch_header_rec.recipe_validity_rule_id);
651 
652          FETCH recipe_validity_rule_cursor
653           INTO l_recipe_validity_rule;
654 
655          CLOSE recipe_validity_rule_cursor;
656 
657          -- Load the recipe data.
658          OPEN recipe_cursor (l_recipe_validity_rule.recipe_id);
659 
660          FETCH recipe_cursor
661           INTO l_recipe;
662 
663          CLOSE recipe_cursor;
664 
665          IF l_recipe.recipe_id IS NULL THEN
666             gme_common_pvt.log_message ('GME_API_INVALID_RULE');
667             RAISE expected_error;
668          END IF;
669 
670          IF g_debug <= gme_debug.g_log_statement THEN
671             gme_debug.put_line (   g_pkg_name
672                                 || '.'
673                                 || l_api_name
674                                 || 'Calling gmd_recipe_data_pub.get_recipe_data');
675          END IF;
676 
677          gmd_recipe_data_pub.get_recipe_data
678               (p_api_version                   => 1
679               ,p_init_msg_list                 => fnd_api.g_false
680               ,p_recipe_id                     => l_recipe.recipe_id
681               ,p_organization_id               => x_batch_header_rec.organization_id
682               ,x_return_status                 => l_return_status
683               ,x_msg_count                     => l_message_count
684               ,x_msg_data                      => l_message_list
685               ,x_return_code                   => l_return_code
686               ,x_recipe_rout_tbl               => gme_common_pvt.routings
687               ,x_recipe_rout_matl_tbl          => gme_common_pvt.routing_materials
688               ,x_recipe_step_out               => gme_common_pvt.steps
689               ,x_routing_depd_tbl              => gme_common_pvt.step_dependencies
690               ,x_oprn_act_out                  => gme_common_pvt.activities
691               ,x_oprn_resc_rec                 => gme_common_pvt.resources
692               ,x_formula_header_rec            => l_formula_master
693               ,x_formula_dtl_tbl               => gme_common_pvt.materials
694               ,x_recp_resc_proc_param_tbl      => gme_common_pvt.process_parameters);
695          IF g_debug <= gme_debug.g_log_statement THEN
696             gme_debug.put_line
697                        (   g_pkg_name
698                         || '.'
699                         || l_api_name
700                         || 'Return from gmd_recipe_data_pub.get_recipe_data '
701                         || l_return_status);
702          END IF;
703 
704       ELSE /* p_creation_mode = 'LCF' */
705       /* Setup following variables so that rest of the program goes through */
706          l_return_status := fnd_api.g_ret_sts_success;
707          l_recipe_validity_rule.inventory_item_id :=
708                                gme_common_pvt.materials (1).inventory_item_id;
709          l_formula_master.text_code := NULL;
710          l_formula_master.scale_type := 0;
711          l_recipe.calculate_step_quantity := 0;
712          IF gme_common_pvt.routings.COUNT > 0 THEN
713             l_recipe.routing_id := gme_common_pvt.routings(1).routing_id;
714          END IF;
715       END IF; /* IF p_creation_mode <> 'LCF' THEN */
716 
717       IF (g_debug = gme_debug.g_log_statement) THEN
718          gme_debug.put_line (   g_pkg_name
719                              || ':Creation mode '
720                              || p_creation_mode
721                              || ' Batch size '
722                              || p_batch_size
723                              || ' '
724                              || p_batch_size_uom);
725          gme_debug.put_line ('Return Status was ' || l_return_status);
726          gme_debug.put_line ('return_code = ' || TO_CHAR (l_return_code) );
727          gme_debug.put_line (   '# of Steps = '
728                              || TO_CHAR (gme_common_pvt.steps.COUNT) );
729          gme_debug.put_line (   '# of Acts  = '
730                              || TO_CHAR (gme_common_pvt.activities.COUNT) );
731          gme_debug.put_line (   '# of Rsrc  = '
732                              || TO_CHAR (gme_common_pvt.resources.COUNT) );
733          gme_debug.put_line (   '# of Matl =  '
734                              || TO_CHAR
735                                        (gme_common_pvt.routing_materials.COUNT) );
736          gme_debug.put_line (   '# of Depd = '
737                              || TO_CHAR
738                                        (gme_common_pvt.step_dependencies.COUNT) );
739          gme_debug.put_line (   '# of Lines = '
740                              || TO_CHAR (gme_common_pvt.materials.COUNT) );
741       END IF;
742 
743       IF l_return_status <> fnd_api.g_ret_sts_success THEN
744          IF l_return_code = 4 THEN
745             -- Recipe does not have a routing, not an error
746             NULL;
747          ELSIF l_return_code = 8 THEN
748             fnd_message.set_name ('GMD', 'GMD_CIRCULAR_DEPEN_DETECT');
749             fnd_msg_pub.ADD;
750             RAISE invalid_recipe;
751          ELSE
752             gme_common_pvt.log_message ('GME_BAD_RECIPE_RETRIEVAL');
753             RAISE invalid_recipe;
754          END IF;
755       END IF;
756 
757       IF gme_common_pvt.routings.COUNT > 0 THEN
758          x_batch_header_rec.enforce_step_dependency :=
759                  NVL (gme_common_pvt.routings (1).enforce_step_dependency, 0);
760       END IF;
761 
762       IF p_creation_mode <> 'LCF' THEN
763          IF    l_formula_master.formula_id IS NULL
764             OR l_formula_master.delete_mark = 1
765             OR l_formula_master.inactive_ind = 1 THEN
766             gme_common_pvt.log_message ('GME_API_INVALID_FORMULA');
767             RAISE expected_error;
768          END IF;
769       END IF;                                /* IF p_creation_mode <> 'LCF' */
770 
771       -- Retrieve and validate formula details
772       l_number_of_formula_lines := 0;
773       l_total_input_qty := 0;
774       l_total_output_qty := 0;
775 
776       IF g_debug <= gme_debug.g_log_statement THEN
777          gme_debug.put_line (   g_pkg_name
778                              || '.'
779                              || l_api_name
780                              || 'Start material processing');
781       END IF;
782 
783       FOR i IN 1 .. gme_common_pvt.materials.COUNT LOOP
784          l_formula_material := gme_common_pvt.materials (i);
785 
786          -- Bug 11815699 - get item status code.
787          -- pawan kumar changed this cursor for bug 4917631
788          -- Bug 7578476 - Fetch primary uom code also.
789          OPEN item_master_cursor (l_formula_material.inventory_item_id
790                                  ,x_batch_header_rec.organization_id);
791          FETCH item_master_cursor
792           INTO l_item_master.inventory_item_id, l_item_master.concatenated_segments,
793                l_item_master.eng_item_flag, l_item_master.process_execution_enabled_flag,
794                l_item_master.primary_uom_code, l_item_master.inventory_item_status_code;
795 
796          -- Bug 13811289 - Make sure this is valid for the specific organization.
797          IF item_master_cursor%NOTFOUND THEN
798             CLOSE item_master_cursor;
799 
800             -- Bug 13811289 - Get item number for any non specific organization.
801             OPEN item_master_descr_cursor (l_formula_material.inventory_item_id);
802             FETCH item_master_descr_cursor INTO l_item_master.concatenated_segments;
803             CLOSE item_master_descr_cursor;
804 
805 
806             gme_common_pvt.log_message (p_product_code => 'GMD'
807                                        ,p_message_code => 'GMD_RCP_ITEMORG_NOT_FOUND'
808                                        ,p_token1_name  => 'ORGN'
809                                        ,p_token1_value => gme_common_pvt.g_organization_code
810                                        ,p_token2_name  => 'ITEM'
811                                        ,p_token2_value => l_item_master.concatenated_segments);
812 
813             RAISE error_count_exceeded;
814          END IF;
815 
816          CLOSE item_master_cursor;
817 
818          -- Bug 11815699 - fetch process execution enabled associated to item status code.
819          l_status_exec_enabled := 'Y';
820          IF l_item_master.inventory_item_status_code IS NOT NULL THEN
821             OPEN  item_status_cursor (l_item_master.inventory_item_status_code);
822             FETCH item_status_cursor INTO l_status_exec_enabled;
823             CLOSE item_status_cursor;
824          END IF;
825 
826 
827          -- Bug 11815699 - consider process exceution enabled associated to item status code also.
828          IF    l_item_master.inventory_item_id IS NULL
829             OR l_item_master.process_execution_enabled_flag = 'N'
830             OR l_status_exec_enabled = 'N'
831             OR (    l_item_master.eng_item_flag = 'Y'
832                 AND x_batch_header_rec.laboratory_ind = 0) THEN
833             gme_common_pvt.log_message ('GME_API_INVALID_ITEM'
834                                        ,'ITEM_NO'
835                                        ,l_item_master.concatenated_segments);
836             RAISE error_count_exceeded;
837          ELSE
838             l_number_of_formula_lines := l_number_of_formula_lines + 1;
839             l_item_masters (l_number_of_formula_lines) := l_item_master;
840 
841             IF l_formula_material.line_type > 0 THEN
842                IF l_formula_material.line_type =
843                                               gme_common_pvt.g_line_type_prod THEN
844                   l_number_of_product_lines := l_number_of_product_lines + 1;
845 
846 
847 
848                ELSE
849                   l_number_of_byproduct_lines :=
850                                               l_number_of_byproduct_lines + 1;
851                END IF;
852             ELSE
853                l_number_of_ingredient_lines :=
854                                              l_number_of_ingredient_lines + 1;
855             END IF;                     /* l_formula_material.line_type > 0 */
856 
857 
858             -- Construct the material detail row
859 
860             gme_common_pvt.construct_material_detail
861                               (p_formula_detail_rec       => l_formula_material
862                               ,p_item_master_rec          => l_item_master
863                               ,p_batch_header_rec         => x_batch_header_rec
864                               ,x_material_detail_rec      => l_gme_material_detail
865                               ,x_return_status            => l_return_status);
866 
867             IF l_return_status = fnd_api.g_ret_sts_success THEN
868 
869                l_material_details (l_number_of_formula_lines) :=
870                                                         l_gme_material_detail;
871 
872                -- Bug 7578476 - Initialize original_qty properly.
873                -- l_material_details (l_number_of_formula_lines).original_qty :=
874                --                                        l_formula_material.qty;
875 
876                l_material_details (l_number_of_formula_lines).original_qty :=
877                         l_material_details (l_number_of_formula_lines).plan_qty;
878 
879                -- Bug 7578476 - Use correct primary UOM to derive original_primary_qty.
880                IF (l_material_details (l_number_of_formula_lines).dtl_um <>
881                                                 l_item_masters(l_number_of_formula_lines).primary_uom_code) THEN
882                   l_temp_qty :=
883                      inv_convert.inv_um_convert
884                         (l_material_details (l_number_of_formula_lines).inventory_item_id
885                         ,5
886                         ,l_material_details (l_number_of_formula_lines).original_qty
887                         ,l_material_details (l_number_of_formula_lines).dtl_um
888                         ,l_item_masters (l_number_of_formula_lines).primary_uom_code
889                         -- ,l_item_master.primary_uom_code
890                         ,NULL
891                         ,NULL);
892                ELSE
893                   l_temp_qty :=
894                      l_material_details (l_number_of_formula_lines).original_qty;
895                END IF;
896 
897                l_material_details (l_number_of_formula_lines).original_primary_qty :=
898                                                                     l_temp_qty;
899             /*  --Pawan  changes for GMO
900               IF  (l_material_details (l_number_of_formula_lines).line_type  =
901                   gme_common_pvt.g_line_type_ing )
902               AND (l_material_details (l_number_of_formula_lines).phantom_type = 0 ) THEN
903 
904                 GMO_DISPENSE_GRP.IS_DISPENSE_ITEM (p_api_version   => 1.0,
905                             p_init_msg_list       => fnd_api.g_false ,
906                             x_return_status       => l_return_status ,
907                             x_msg_count           => l_message_count ,
908                             x_msg_data            => l_message_list ,
909                             p_inventory_item_id   => l_formula_material.inventory_item_id,
910                             p_organization_id     => x_batch_header_rec.organization_id,
911                             p_recipe_id           => l_recipe.recipe_id,
912                             x_dispense_required   => l_dispense_required,
913                             x_dispense_config_id  => l_config_id);
914 
915                 IF l_return_status = fnd_api.g_ret_sts_success THEN
916                     l_material_details (l_number_of_formula_lines).dispense_ind :=  l_dispense_required ;
917                 END IF;
918 
919              END IF;
920               -- GMO changes end   */
921             ELSE
922                RAISE error_count_exceeded;
923             END IF;
924          END IF;              /* l_item_master.inventory_item_id IS NULL OR */
925       END LOOP;             /* l_formula_material IN formula_details_cursor */
926 
927       IF g_debug <= gme_debug.g_log_statement THEN
928          gme_debug.put_line (   g_pkg_name
929                              || '.'
930                              || l_api_name
931                              || 'Finished material processing');
932       END IF;
933 
934       IF    l_number_of_formula_lines = 0
935          OR l_number_of_ingredient_lines = 0
936          OR l_number_of_product_lines = 0 THEN
937          gme_common_pvt.log_message ('GME_API_INVALID_FORMULA');
938          RAISE error_count_exceeded;
939       END IF;
940 
941       -- We now need to sort out the scaling. If the formula is marked as scalable
942       -- we have to work out the output and input quantities. The columns on
943       -- the total_output_qty and total_input_qty on the formula header express
944       -- the totals in the YIELD_UOM of the system. However these are not always
945       -- useful and we have to work out other quantities on an as-required basis.
946       IF l_formula_master.scale_type = 1 THEN
947          -- The formula is scalable (at least at the header level anyway)
948          -- The first thing we need to do is find out the scale factor
949          IF p_creation_mode = 'OUTPUT' THEN
950             -- Batch is being created by Total Output.
951             -- Scale Factor is the requested batch size divided by the recipe
952             -- total output qty
953             l_total_output_qty := 0;
954             l_uom := p_batch_size_uom;
955             gmd_common_val.calculate_total_qty
956                                   (formula_id            => l_formula_master.formula_id
957                                   ,x_product_qty         => l_total_output_qty
958                                   ,x_ingredient_qty      => l_total_input_qty
959                                   ,x_uom                 => l_uom
960                                   ,x_return_status       => l_return_status
961                                   ,x_msg_count           => l_message_count
962                                   ,x_msg_data            => l_message_list);
963 
964             /* If the above procedure is not able to calculate one of the 2 total qty's it returns status of Q. We need to
965             check if the total_output_qty is calculated correctly and not worry about if the total_input is notcalculated. */
966             IF     (l_return_status <> fnd_api.g_ret_sts_success)
967                AND (l_return_status <> 'Q') THEN
968                RAISE expected_error;
969             END IF;
970 
971             IF (l_total_output_qty IS NULL AND l_return_status = 'Q') THEN
972                fnd_message.set_name ('GMD', 'GMD_ERR_CALC_OUTPUT');
973                fnd_message.set_token ('UOM', l_uom);
974                fnd_msg_pub.ADD;
975                RAISE expected_error;
976             END IF;
977 
978             gmd_validity_rules.get_output_ratio
979                         (p_formula_id          => l_formula_master.formula_id
980                         ,p_batch_output        => p_batch_size
981                         ,p_formula_output      => l_total_output_qty
982                         ,p_yield_um            => l_uom
983                         ,x_return_status       => l_return_status
984                         ,x_output_ratio        => gme_common_pvt.g_batch_scale_factor);
985 
986             IF l_return_status <> fnd_api.g_ret_sts_success THEN
987                RAISE expected_error;
988             END IF;
989 
990             l_primaries := 'OUTPUTS';
991          ELSIF p_creation_mode = 'PRODUCT' THEN
992             -- Batch is being created by Product and Quantity. Similar to above, but
993             -- the scale factor is the requested batch size divided by the quantity of
994             -- this item produced by the formula, so we need to calulate this first.
995             -- Although unlikely the specified product could occur multiple times
996             -- and be both a product and a byproduct.
997             l_total_output_qty := 0;
998             l_uom := p_batch_size_uom;
999 
1000             /* Let's convert formula product quantity in the requested UOM */
1001             FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1002                IF     l_material_details (loop_count).line_type =
1003                                               gme_common_pvt.g_line_type_prod
1004                   AND l_material_details (loop_count).inventory_item_id =
1005                                       l_recipe_validity_rule.inventory_item_id THEN
1006 
1007                   -- bug#5373369 nsinghi rework. While determining the scale factor, give higher precision,
1008                   -- otherwise when converting back to batch UOM, there is decimal dust issue and batch
1009                   -- creation fails.
1010                   l_temp_qty :=
1011                      inv_convert.inv_um_convert
1012                            (l_material_details (loop_count).inventory_item_id
1013                            ,32 --5
1014                            ,l_material_details (loop_count).plan_qty
1015                            ,l_material_details (loop_count).dtl_um
1016                            ,l_uom
1017                            ,NULL
1018                            ,NULL);
1019 
1020                   IF l_temp_qty < 0 THEN
1021                      IF (g_debug = gme_debug.g_log_statement) THEN
1022                         gme_debug.put_line
1023                            ('Failed in UOM Conv from formula product UOM to requested UOM');
1024                      END IF;
1025 
1026                      l_item_id :=
1027                              l_material_details (loop_count).inventory_item_id;
1028                      l_from_uom := l_material_details (loop_count).dtl_um;
1029                      l_to_uom := l_uom;
1030                      RAISE conversion_failure;
1031                   ELSE
1032                      l_total_output_qty := l_total_output_qty + l_temp_qty;
1033                      -- Bug 7565054 - Rework of bug 7284242.
1034                      -- If p_sum_all_prod_lines is not 'A' then sum only the first matching product line.
1035                      EXIT WHEN p_sum_all_prod_lines <> 'A'; -- Exit the loop. Only sum the first matching product
1036                   END IF;
1037                END IF;
1038                   /* l_material_details(loop_count).line_type IN (1, 2) AND */
1039             END LOOP;       /* loop_count IN 1 .. l_number_of_formula_lines */
1040 
1041             l_primaries := 'OUTPUTS';
1042 
1043             IF l_total_output_qty = 0 THEN
1044                gme_common_pvt.log_message ('GME_API_PROD_QTY_CANT_ZERO');
1045                RAISE expected_error;
1046             END IF;
1047 
1048             -- Bug 7565054 - Back out 7284242
1049             -- reinstate original calculation but total output may not include all product lines now.
1050             gme_common_pvt.g_batch_scale_factor :=
1051                                              p_batch_size / l_total_output_qty;
1052 
1053          ELSIF p_creation_mode = 'RECIPE' THEN
1054             -- Batch is being created by Recipe and Version
1055             -- If there is a production rule in force we must find the batch size
1056             -- allowable for this plant/product. The scale factor is then this size
1057             -- divided by the formula's output of this product. If there isn't a
1058             -- production rule then the formula as it stands is what we will
1059             -- create the batch with, and scaling is thus not needed.
1060             OPEN production_rules_cursor
1061                                    (l_recipe_validity_rule.inventory_item_id
1062                                    ,x_batch_header_rec.organization_id);
1063 
1064             FETCH production_rules_cursor
1065              INTO l_production_rule_qty, l_production_um;
1066 
1067             IF production_rules_cursor%NOTFOUND THEN
1068                l_primaries := 'OUTPUTS';
1069                gme_common_pvt.g_batch_scale_factor := 1;
1070 
1071                IF (g_debug = gme_debug.g_log_statement) THEN
1072                   gme_debug.put_line
1073                                 ('CREATING BY RECIPE/VERSION WITHOUT SCALING');
1074                END IF;
1075             ELSE
1076                l_total_output_qty := 0;
1077 
1078                FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1079                   IF     l_material_details (loop_count).line_type IN
1080                             (gme_common_pvt.g_line_type_prod
1081                             ,gme_common_pvt.g_line_type_byprod)
1082                      AND l_material_details (loop_count).inventory_item_id =
1083                                       l_recipe_validity_rule.inventory_item_id THEN
1084 
1085                      -- bug#5373369 nsinghi rework. While determining the scale factor, give higher precision, otherwise when converting back to batch UOM, there is decimal dust issue and batch creation fails.
1086 
1087                      l_temp_qty :=
1088                         inv_convert.inv_um_convert
1089                            (l_material_details (loop_count).inventory_item_id
1090                            ,32 --5
1091                            ,l_material_details (loop_count).plan_qty
1092                            ,l_material_details (loop_count).dtl_um
1093                            ,l_production_um
1094                            ,NULL
1095                            ,NULL);
1096 
1097                      IF l_temp_qty < 0 THEN
1098                         IF (g_debug = gme_debug.g_log_statement) THEN
1099                            gme_debug.put_line
1100                               ('Failed in UOM Conv from formula product UOM to requested UOM');
1101                         END IF;
1102 
1103                         l_item_id :=
1104                              l_material_details (loop_count).inventory_item_id;
1105                         l_from_uom := l_material_details (loop_count).dtl_um;
1106                         l_to_uom := l_production_um;
1107                         RAISE conversion_failure;
1108                      ELSE
1109                         l_total_output_qty := l_total_output_qty + l_temp_qty;
1110                      END IF;
1111                   END IF;
1112                   /* l_material_details(loop_count).line_type IN (1, 2) AND */
1113                END LOOP;    /* loop_count IN 1 .. l_number_of_formula_lines */
1114 
1115                IF l_total_output_qty = 0 THEN
1116                   gme_common_pvt.log_message ('GME_API_PROD_QTY_CANT_ZERO');
1117                   RAISE expected_error;
1118                END IF;
1119 
1120                gme_common_pvt.g_batch_scale_factor :=
1121                                     l_production_rule_qty / l_total_output_qty;
1122             END IF;                  /* IF production_rules_cursor%NOTFOUND */
1123 
1124             CLOSE production_rules_cursor;
1125 
1126             l_primaries := 'OUTPUTS';
1127          ELSIF p_creation_mode = 'INPUT' THEN
1128             -- Batch is being created by Total Input. The scale factor is the requested batch size divided by the formula's
1129             -- total input. We should be changing all the ingredients to the batch size UOM
1130             l_total_input_qty := 0;
1131             l_uom := p_batch_size_uom;
1132             gmd_common_val.calculate_total_qty
1133                                   (formula_id            => l_formula_master.formula_id
1134                                   ,x_product_qty         => l_total_output_qty
1135                                   ,x_ingredient_qty      => l_total_input_qty
1136                                   ,x_uom                 => l_uom
1137                                   ,x_return_status       => l_return_status
1138                                   ,x_msg_count           => l_message_count
1139                                   ,x_msg_data            => l_message_list);
1140 
1141             IF     (l_return_status <> fnd_api.g_ret_sts_success)
1142                AND (l_return_status <> 'Q') THEN
1143                RAISE expected_error;
1144             END IF;
1145 
1146             IF (l_total_input_qty IS NULL AND l_return_status = 'Q') THEN
1147                fnd_message.set_name ('GMD', 'GMD_ERR_CALC_OUTPUT');
1148                fnd_message.set_token ('UOM', l_uom);
1149                fnd_msg_pub.ADD;
1150                RAISE expected_error;
1151             END IF;
1152 
1153             gmd_validity_rules.get_batchformula_ratio
1154                   (p_formula_id              => l_formula_master.formula_id
1155                   ,p_batch_input             => p_batch_size
1156                   ,p_formula_input           => l_total_input_qty
1157                   ,p_yield_um                => l_uom
1158                   ,x_return_status           => l_return_status
1159                   ,x_batchformula_ratio      => gme_common_pvt.g_batch_scale_factor);
1160 
1161             IF l_return_status <> fnd_api.g_ret_sts_success THEN
1162                RAISE expected_error;
1163             END IF;
1164 
1165             l_primaries := 'INPUTS';
1166          ELSIF p_creation_mode = 'LCF' THEN
1167             -- No need to do anything, but this is a valid creation mode
1168             NULL;
1169          ELSE
1170             -- Batch is being created by means unknown
1171             gme_common_pvt.log_message ('GME_API_UNSUPPORTED_MODE'
1172                                        ,'MODE'
1173                                        ,p_creation_mode);
1174             RAISE expected_error;
1175          END IF;
1176 
1177          IF gme_common_pvt.routings.COUNT <> 0 THEN
1178             l_total_output_qty_c := 0;
1179 
1180             FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1181                IF l_material_details (loop_count).line_type IN
1182                      (gme_common_pvt.g_line_type_prod
1183                      ,gme_common_pvt.g_line_type_byprod) THEN
1184                   IF l_material_details (loop_count).dtl_um =
1185                                       gme_common_pvt.routings (1).routing_uom THEN
1186                      l_total_output_qty_c :=
1187                           l_total_output_qty_c
1188                         + l_material_details (loop_count).plan_qty;
1189                   ELSE
1190                      l_temp_qty :=
1191                         inv_convert.inv_um_convert
1192                            (l_material_details (loop_count).inventory_item_id
1193                            ,32 -- Bug 16474091 - change precision from 5 to 32
1194                            ,l_material_details (loop_count).plan_qty
1195                            ,l_material_details (loop_count).dtl_um
1196                            ,gme_common_pvt.routings (1).routing_uom
1197                            ,NULL
1198                            ,NULL);
1199 
1200                      IF l_temp_qty < 0 THEN
1201                         IF (g_debug = gme_debug.g_log_statement) THEN
1202                            gme_debug.put_line
1203                               ('Failed in UOM Conv from formula product UOM to routing UOM');
1204                         END IF;
1205 
1206                         l_item_id :=
1207                              l_material_details (loop_count).inventory_item_id;
1208                         l_from_uom := l_material_details (loop_count).dtl_um;
1209                         l_to_uom := gme_common_pvt.routings (1).routing_uom;
1210                         RAISE conversion_failure;
1211                      ELSE
1212                         l_total_output_qty_c :=
1213                                             l_total_output_qty_c + l_temp_qty;
1214                      END IF;
1215                   END IF;            /* If formula detail UOM = routing UOM */
1216                END IF;
1217                       /* l_material_details(loop_count).line_type IN (1, 2) */
1218             END LOOP;       /* loop_count IN 1 .. l_number_of_formula_lines */
1219 
1220             IF (g_debug = gme_debug.g_log_statement) THEN
1221                gme_debug.put_line (   'tot_output before scaling is '
1222                                    || TO_CHAR (l_total_output_qty_c) );
1223             END IF;
1224          END IF;                   /* IF gme_common_pvt.routings.COUNT <> 0 */
1225 
1226          -- Bug 10624995 - rearrange logic as to handle integer scale items for non scaled batches.
1227          l_change_made := 0;
1228          IF gme_common_pvt.g_batch_scale_factor <> 1 THEN
1229             IF (g_debug = gme_debug.g_log_statement) THEN
1230                gme_debug.put_line
1231                                (   'scale factor is '
1232                                 || TO_CHAR
1233                                           (gme_common_pvt.g_batch_scale_factor) );
1234             END IF;
1235 
1236             l_change_made := 1;
1237 
1238             /* Following line is added, because the scale_batch is expecting the
1239                batch status to be 0. We will reset it to 1 as soon as scaling is done */
1240             x_batch_header_rec.batch_status := 0;
1241             /* l_over_allocations parameter is used to handle default lot going  */
1242             /* negative cases, which would not be a case here as the default lot */
1243             /* is created after the scale is successfull                         */
1244             l_in_material_details := l_material_details;
1245             gme_scale_batch_pvt.scale_batch
1246                (p_batch_header_rec            => x_batch_header_rec
1247                ,p_material_tbl                => l_in_material_details
1248                ,p_scale_factor                => gme_common_pvt.g_batch_scale_factor
1249                ,p_primaries                   => l_primaries
1250                ,p_qty_type                    => 1
1251                ,p_validity_rule_id            => l_recipe_validity_rule.recipe_validity_rule_id
1252                ,p_enforce_vldt_check          => fnd_api.g_true
1253                ,p_recalc_dates                => fnd_api.g_false
1254                ,p_use_workday_cal             => fnd_api.g_false
1255                ,p_contiguity_override         => fnd_api.g_true
1256                ,x_material_tbl                => l_material_details
1257                ,x_exception_material_tbl      => l_exception_material_tbl
1258                ,x_batch_header_rec            => l_in_batch_header
1259                ,
1260             /* Create batch does not need any values from here so dummy variable */
1261                 x_return_status               => x_return_status);
1262 
1263             x_batch_header_rec.batch_status := gme_common_pvt.g_batch_pending;
1264 
1265             IF (g_debug = gme_debug.g_log_statement) THEN
1266                gme_debug.put_line (   'return from scale_batch is: '
1267                                    || x_return_status);
1268             END IF;
1269 
1270             IF x_return_status <> fnd_api.g_ret_sts_success THEN
1271                RAISE scaling_failure;
1272             ELSE
1273                FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1274                   l_material_details (loop_count).plan_qty :=
1275                          ROUND (l_material_details (loop_count).plan_qty, 32);
1276                   l_material_details (loop_count).original_qty :=
1277                      ROUND (l_material_details (loop_count).original_qty, 32);
1278 
1279                   -- Bug 7578476 - Use already loaded primary UOM to derive original_primary_qty.
1280                   -- Remove unnecessary fetch using cursor production_rules_cursor.
1281                   IF (l_material_details (loop_count).dtl_um <> l_item_masters(loop_count).primary_uom_code) THEN
1282                     l_temp_qty := inv_convert.inv_um_convert
1283                                  (l_material_details (loop_count).inventory_item_id
1284                                  ,5
1285                                  ,l_material_details (loop_count).original_qty
1286                                  ,l_material_details (loop_count).dtl_um
1287                                  ,l_item_masters(loop_count).primary_uom_code
1288                                  ,NULL
1289                                  ,NULL);
1290                  ELSE
1291                     l_temp_qty := l_material_details (loop_count).original_qty;
1292                  END IF;
1293                  l_material_details (loop_count).original_primary_qty := l_temp_qty;
1294                END LOOP;
1295             END IF;
1296          -- Bug 10624995 - Handle integer scale items if the batch does not require scaling.
1297          ELSE
1298             -- Let's make sure integer scale items are correct.
1299             FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1300                IF (l_material_details (loop_count).scale_type = 2) THEN
1301                    l_change_made := 1;
1302                    l_scale_rec.scale_rounding_variance := l_material_details (loop_count).scale_rounding_variance;
1303                    l_scale_rec.qty := l_material_details (loop_count).plan_qty;
1304                    l_scale_rec.scale_multiple := l_material_details (loop_count).scale_multiple;
1305                    l_scale_rec.rounding_direction := l_material_details (loop_count).rounding_direction;
1306 
1307 	           IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
1308                      gme_debug.put_line('values going to int mult scale are: ');
1309                      gme_debug.put_line('qty '||l_scale_rec.qty);
1310                      gme_debug.put_line('rnd variance '||l_scale_rec.scale_rounding_variance);
1311                      gme_debug.put_line('multiple '||l_scale_rec.scale_multiple);
1312                      gme_debug.put_line('rnd direction '||l_scale_rec.rounding_direction);
1313                    END IF;
1314 
1315 	           gmd_common_scale.integer_multiple_scale
1316                       (  p_scale_rec          => l_scale_rec
1317                         ,x_scale_rec          => l_scale_rec_out
1318                         ,x_return_status      => l_return_status
1319                       );
1320 
1321 	           IF l_return_status <> FND_API.G_RET_STS_SUCCESS THEN
1322                       RAISE error_in_integer_scale;
1323                    END IF;
1324 
1325                    l_material_details (loop_count).plan_qty := l_scale_rec_out.qty;
1326                    l_material_details (loop_count).original_qty := l_scale_rec_out.qty;
1327 
1328                    IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
1329                       gme_debug.put_line('plan actual after integer scaling is '||l_material_details (loop_count).plan_qty);
1330                    END IF;
1331                END IF; /* l_material_detail_rec.scale_type = 2 */
1332             END LOOP;
1333             -- End herbal life fix.
1334          END IF;             /* IF gme_common_pvt.g_batch_scale_factor <> 1 */
1335 
1336          -- If scaling or integer logic made a change then calculate values for process loss.
1337          IF l_change_made = 1 THEN
1338             -- We now need to calculate the total scaled formula output in the Routing
1339             -- UOM so that we can look up a few things in the process loss table.
1340             IF gme_common_pvt.routings.COUNT <> 0 THEN
1341                l_total_output_qty_b := 0;
1342 
1343                FOR loop_count IN 1 .. l_number_of_formula_lines LOOP
1344                   IF l_material_details (loop_count).line_type IN
1345                         (gme_common_pvt.g_line_type_prod
1346                         ,gme_common_pvt.g_line_type_byprod) THEN
1347                      IF l_material_details (loop_count).dtl_um =
1348                                       gme_common_pvt.routings (1).routing_uom THEN
1349                         l_total_output_qty_b :=
1350                              l_total_output_qty_b
1351                            + l_material_details (loop_count).plan_qty;
1352                      ELSE
1353                         l_temp_qty :=
1354                            inv_convert.inv_um_convert
1355                               (l_material_details (loop_count).inventory_item_id
1356                               ,32  -- Bug 16474091 - change precision from 5 to 32
1357                               ,l_material_details (loop_count).plan_qty
1358                               ,l_material_details (loop_count).dtl_um
1359                               ,gme_common_pvt.routings (1).routing_uom
1360                               ,NULL
1361                               ,NULL);
1362 
1363                         IF l_temp_qty < 0 THEN
1364                            IF (g_debug = gme_debug.g_log_statement) THEN
1365                               gme_debug.put_line
1366                                  ('Failed in UOM Conv from formula product UOM to routing UOM');
1367                            END IF;
1368 
1369                            l_item_id :=
1370                               l_material_details (loop_count).inventory_item_id;
1371                            l_from_uom :=
1372                                         l_material_details (loop_count).dtl_um;
1373                            l_to_uom := gme_common_pvt.routings (1).routing_uom;
1374                            RAISE conversion_failure;
1375                         ELSE
1376                            l_total_output_qty_b :=
1377                                             l_total_output_qty_b + l_temp_qty;
1378                         END IF;                           /* l_temp_qty > 0 */
1379                      END IF;        /* IF routing and formula uoms are same */
1380                   END IF;                               /* If line type > 0 */
1381                END LOOP;
1382 
1383                IF (g_debug = gme_debug.g_log_statement) THEN
1384                   gme_debug.put_line (   'Total Output after scaling is '
1385                                       || TO_CHAR (l_total_output_qty_b) );
1386                END IF;
1387             END IF;             /* IF gme_common_pvt.routings.COUNT <> 0 */
1388          END IF;                /* IF l_change_made */
1389 
1390          IF p_creation_mode <> 'LCF' THEN
1391             -- Batch has been scaled OK so we now need to determine and apply the process loss.
1392             l_process_loss :=
1393                gme_common_pvt.get_process_loss
1394                   (p_validity_rule_id                => l_recipe_validity_rule.recipe_validity_rule_id
1395                   ,p_organization_id                 => x_batch_header_rec.organization_id
1396                   ,p_total_output_qty_scaled         => l_total_output_qty_b
1397                   ,p_total_output_qty_pre_scale      => l_total_output_qty_c);
1398 
1399             IF (l_process_loss IS NULL) THEN
1400                RAISE expected_error;
1401             END IF;
1402 
1403             -- Now that the process loss is known, we need to gross up the scalable
1404             -- ingredients (for creation by Total Output, Product or Recipe) or
1405             -- scale down the scalable products (for creation by Total Input).
1406             FOR l_row_count IN 1 .. l_number_of_formula_lines LOOP
1407                IF l_material_details (l_row_count).line_type < 0 THEN
1408                   IF     p_creation_mode IN ('PRODUCT', 'OUTPUT', 'RECIPE')
1409                      AND l_material_details (l_row_count).scale_type = 1 THEN
1410                      l_material_details (l_row_count).plan_qty :=
1411                           l_material_details (l_row_count).plan_qty
1412                         * 100
1413                         / (100 - l_process_loss);
1414                   END IF;
1415                ELSE       /* l_material_details(l_row_count).line_type >= 0 */
1416                   IF p_creation_mode = 'INPUT' THEN
1417                      l_material_details (l_row_count).plan_qty :=
1418                           l_material_details (l_row_count).plan_qty
1419                         * (100 - l_process_loss)
1420                         / 100;
1421                   END IF;
1422                END IF;  /* IF l_material_details(l_row_count).line_type < 0 */
1423 
1424                -- Bug 7656415 - Let's round the plan qty.
1425                l_material_details (l_row_count).plan_qty :=
1426                                    ROUND(l_material_details (l_row_count).plan_qty,5);
1427 
1428                l_material_details (l_row_count).original_qty :=
1429                                      l_material_details (l_row_count).plan_qty;
1430 
1431                -- 7578476 - Initialize original_primary_qty properly.
1432                IF (l_material_details (l_row_count).dtl_um <>
1433                                                 l_item_masters(l_row_count).primary_uom_code) THEN
1434                   l_material_details (l_row_count).original_primary_qty :=
1435                      inv_convert.inv_um_convert
1436                         (l_material_details (l_row_count).inventory_item_id
1437                         ,5
1438                         ,l_material_details (l_row_count).original_qty
1439                         ,l_material_details (l_row_count).dtl_um
1440                         ,l_item_masters(l_row_count).primary_uom_code
1441                         ,NULL
1442                         ,NULL);
1443                ELSE
1444                   l_material_details (l_row_count).original_primary_qty :=
1445                                       l_material_details (l_row_count).original_qty;
1446                END IF;
1447             END LOOP;      /* l_row_count IN 1 .. l_number_of_formula_lines */
1448 
1449             IF (g_debug = gme_debug.g_log_statement) THEN
1450                gme_debug.put_line (   'Total Output after Process Loss is '
1451                                    || TO_CHAR (l_total_output_qty_b) );
1452             END IF;
1453          END IF;                        /* IF p_creation_mode <> 'LCF' THEN */
1454 
1455          IF gme_common_pvt.routings.COUNT <> 0 THEN
1456             -- Accumulate the total output of the batch in the ROUTING UOM
1457             l_requested_qty := 0;
1458 
1459             IF    (l_total_output_qty_b IS NULL OR l_total_output_qty_b = 0)
1460                OR (p_creation_mode = 'INPUT' AND l_process_loss <> 0) THEN
1461                l_total_output_qty_b := 0;
1462 
1463                FOR l_row_count IN 1 .. l_number_of_formula_lines LOOP
1464                   IF l_material_details (l_row_count).line_type > 0 THEN
1465                      IF l_material_details (l_row_count).dtl_um =
1466                                       gme_common_pvt.routings (1).routing_uom THEN
1467                         l_total_output_qty_b :=
1468                              l_total_output_qty_b
1469                            + l_material_details (l_row_count).plan_qty;
1470                      ELSE
1471                         l_temp_qty :=
1472                            inv_convert.inv_um_convert
1473                               (l_material_details (l_row_count).inventory_item_id
1474                               ,5
1475                               ,l_material_details (l_row_count).plan_qty
1476                               ,l_material_details (l_row_count).dtl_um
1477                               ,gme_common_pvt.routings (1).routing_uom
1478                               ,NULL
1479                               ,NULL);
1480 
1481                         IF l_temp_qty < 0 THEN
1482                            l_item_id :=
1483                               l_material_details (l_row_count).inventory_item_id;
1484                            l_from_uom :=
1485                                       l_material_details (l_row_count).dtl_um;
1486                            l_to_uom :=
1487                                       gme_common_pvt.routings (1).routing_uom;
1488                            RAISE conversion_failure;
1489                         ELSE
1490                            l_total_output_qty_b :=
1491                                             l_total_output_qty_b + l_temp_qty;
1492                         END IF;
1493                      END IF;
1494                   END IF;  -- IF l_material_details(l_row_count).line_type > 0
1495                END LOOP;      -- l_row_count IN 1 .. l_number_of_formula_lines
1496             END IF;                         /* b_total_output_qty_b IS NULL */
1497 
1498             IF l_total_output_qty_c = 0 THEN
1499                gme_common_pvt.log_message ('GME_API_PROD_QTY_CANT_ZERO');
1500                RAISE expected_error;
1501             END IF;
1502 
1503             gme_common_pvt.g_routing_scale_factor :=
1504                                    l_total_output_qty_b / l_total_output_qty_c;
1505 
1506             IF (g_debug = gme_debug.g_log_statement) THEN
1507                gme_debug.put_line (   'Routing scale factor is '
1508                                    || gme_common_pvt.g_routing_scale_factor);
1509             END IF;
1510          END IF;                   /* IF gme_common_pvt.routings.COUNT <> 0 */
1511       ELSE                           /* IF l_formula_master.scale_type <> 1 */
1512          -- Formula cannot be scaled
1513          gme_common_pvt.g_batch_scale_factor := 1;
1514          gme_common_pvt.g_routing_scale_factor := 1;
1515       END IF;
1516 
1517       -- Fixed Process Loss ME
1518 
1519       IF (g_debug = gme_debug.g_log_statement) THEN
1520           gme_debug.put_line ('Before calling the Fixed Proccess Loss '
1521                               || p_batch_header_rec.fixed_process_loss_applied);
1522       END IF;
1523 
1524       IF(p_batch_header_rec.fixed_process_loss_applied = 'Y') THEN
1525          l_batch_header_rec := x_batch_header_rec;
1526          l_in_material_details := l_material_details;
1527          gme_fpl_pvt.apply_fixed_process_loss
1528                   (p_batch_header_rec         => l_batch_header_rec
1529                   ,p_material_tbl             => l_in_material_details
1530                   ,p_organization_id          => l_batch_header_rec.organization_id
1531                   ,p_creation_mode            => p_creation_mode
1532                   ,p_called_from              => 1
1533                   ,x_batch_header_rec         => x_batch_header_rec
1534                   ,x_material_tbl             => l_material_details
1535                   ,x_return_status            => x_return_status
1536                   );
1537             IF (g_debug = gme_debug.g_log_statement) THEN
1538                gme_debug.put_line ('Return status after apply Fixed Proccess Loss '
1539                               || x_return_status);
1540             END IF;
1541          IF x_return_status <> fnd_api.g_ret_sts_success THEN
1542             RAISE Fixed_process_loss_failure;
1543          ELSE
1544             IF (g_debug = gme_debug.g_log_statement) THEN
1545               gme_debug.put_line ('Return from Apply Fixed Proccess Loss is ' || x_return_status);
1546             END IF;
1547          END IF;
1548       END IF;
1549 
1550       -- Fixed Process Loss ME
1551       IF (g_debug = gme_debug.g_log_statement) THEN
1552           gme_debug.put_line ('After calling Apply Fixed Proccess Loss return is' || x_return_status);
1553           gme_debug.put_line ('fnd return is ' || fnd_api.g_ret_sts_success);
1554       END IF;
1555 
1556       -- If we've found any errors, don't start the updates.
1557 --      IF gme_common_pvt.g_error_count > 0 THEN
1558   --       RAISE expected_error;
1559     --  END IF;
1560 
1561       IF g_debug <= gme_debug.g_log_statement THEN
1562          gme_debug.put_line (   g_pkg_name
1563                              || '.'
1564                              || l_api_name
1565                              || 'Start dbl pcrocessing');
1566       END IF;
1567 
1568       -- Data construction complete so start the database phase
1569       x_batch_header_rec.formula_id := l_formula_master.formula_id;
1570       x_batch_header_rec.routing_id := l_recipe.routing_id;
1571       -- From here on all errors are fatal so the validation level is not checked.
1572       l_in_batch_header := x_batch_header_rec;
1573       /*5698727 rework Begin we use timestamp initially as its unique. later we update
1574         with actual batch_no
1575       gme_common_pvt.create_document_no (l_in_batch_header
1576                                         ,x_batch_header_rec);*/
1577       SELECT trim(TO_CHAR(systimestamp,'DD:MM:YYYY HH24:MI:SS:FF6')) INTO l_doc_timestamp FROM DUAL;
1578 
1579       IF g_debug <= gme_debug.g_log_statement THEN
1580          gme_debug.put_line (   g_pkg_name
1581                              || '.'
1582                              || l_api_name
1583                              || 'Initial Doc No(timestamp): '||l_doc_timestamp);
1584       END IF;
1585 
1586       IF l_doc_numbering = gme_common_pvt.g_auto_doc_numbering THEN
1587          x_batch_header_rec.batch_no := l_doc_timestamp;
1588       END IF;
1589       --5698727  rework End
1590 
1591       IF x_batch_header_rec.batch_no IS NULL THEN
1592          -- Report error that document number was invalid or could not be generated
1593          RAISE unexpected_error;
1594       ELSE
1595         IF (x_batch_header_rec.batch_type = 0) THEN
1596           l_prefix := FND_PROFILE.VALUE('GME_BATCH_PREFIX');
1597         ELSE
1598           l_prefix := FND_PROFILE.VALUE('GME_FPO_PREFIX');
1599         END IF;
1600         /*5698727  rework commented the following code. We will validate the wip entity
1601           when we are updating the wip_entities table later once the actual doc_no is available */
1602           /* Bug6398619 we have to validate the batch no for the manual doc ordering as
1603              the time stamp is  not created for the manual ordering */
1604           IF l_doc_numbering <> gme_common_pvt.g_auto_doc_numbering THEN
1605               validate_wip_entity(p_organization_id => x_batch_header_rec.organization_id,
1606                             p_batch_no        => l_prefix||x_batch_header_rec.batch_no,
1607                             x_return_status   => l_return_status);
1608             IF l_return_status <> fnd_api.g_ret_sts_success THEN
1609               RAISE wip_entity_err;
1610             END IF;
1611           END IF;
1612       END IF;
1613 
1614 
1615       l_number_of_text_lines := 0;
1616 
1617       --Bug#5112133 add some debug messages for copy formula text GME Parameter
1618       IF (g_debug = gme_debug.g_log_statement) THEN
1619           gme_debug.put_line ('copy_formula_text_ind = '||gme_common_pvt.g_copy_formula_text_ind);
1620       END IF;
1621       -- If the formula has text and we have to copy it then generate
1622       -- the text header row first as database constraints impose this
1623       IF     gme_common_pvt.g_copy_formula_text_ind = 1
1624          AND l_formula_master.text_code IS NOT NULL THEN
1625          l_return :=
1626                 gme_text_dbl.insert_header_row (l_text_header, l_text_header);
1627 
1628          IF l_return THEN
1629             x_batch_header_rec.text_code := l_text_header.text_code;
1630          ELSE
1631             --Bug#5112133
1632             IF (g_debug = gme_debug.g_log_statement) THEN
1633               gme_debug.put_line ('Error in inserting text code = '||l_formula_master.text_code);
1634             END IF;
1635             -- We could not insert the text header. Panic
1636             RAISE expected_error;
1637          END IF;
1638       END IF;
1639 
1640       /* update automatic_step_calculation */
1641       x_batch_header_rec.automatic_step_calculation :=
1642                                               l_recipe.calculate_step_quantity;
1643 
1644       IF l_recipe.routing_id IS NOT NULL THEN
1645          x_batch_header_rec.poc_ind := 'Y';
1646       ELSE
1647          x_batch_header_rec.poc_ind := 'N';
1648       END IF;
1649       -- Pawan Added code for enhanced_pi_ind--GMO
1650       IF p_creation_mode <> 'LCF' THEN
1651          gmd_recipe_fetch_pub.FETCH_ENHANCED_PI_IND (
1652              p_recipe_id                    => l_recipe.recipe_id
1653             ,p_recipe_validity_rule_id      => l_recipe_validity_rule.recipe_validity_rule_id
1654             ,x_enhanced_pi_ind              => l_enhanced_pi_ind
1655             ,x_return_status               =>  l_return_status);
1656             IF l_return_status <> fnd_api.g_ret_sts_success THEN
1657                RAISE expected_error;
1658             END IF;
1659             x_batch_header_rec.ENHANCED_PI_IND  := l_enhanced_pi_ind  ;
1660        ELSE
1661        -- Kapil Bug# 5458674. To Pass the PI Indicator for LCF Batches
1662         x_batch_header_rec.ENHANCED_PI_IND := p_batch_header_rec.enhanced_pi_ind;
1663       END IF; /* IF p_creation_mode <> 'LCF' */
1664 
1665       --FPBug#4395561 Start
1666       /* call create flex procedure to insert the default values of the BACTH_FLEX
1667           DFF's segments if they are enabled */
1668        gme_validate_flex_fld_pvt.create_flex_batch_header(x_batch_header_rec,
1669                                                           x_batch_header_rec,
1670                                                           l_return_status);
1671        IF l_return_status <> FND_API.g_ret_sts_success THEN
1672          RAISE create_flex_failure;
1673        END IF;
1674        --FPBug#4395561 End
1675 
1676       /* This is not a migrated batch, so let's indicate so. */
1677       x_batch_header_rec.migrated_batch_ind := 'N';
1678       l_return :=
1679          gme_batch_header_dbl.insert_row (x_batch_header_rec
1680                                          ,x_batch_header_rec);
1681 
1682       -- If header was inserted OK, then insert the material details. As
1683       -- above, if we are copying text, generate and insert the text and codes first
1684       IF l_return = TRUE THEN
1685 
1686          IF x_batch_header_rec.text_code IS NOT NULL THEN
1687             --Bug#5112133
1688             IF (g_debug = gme_debug.g_log_statement) THEN
1689              gme_debug.put_line ('x_batch_header_rec.text_code = '||x_batch_header_rec.text_code);
1690              gme_debug.put_line ('Inserting formula header text in batch header edit text');
1691             END IF;
1692             FOR l_fm_text_tbl_row IN
1693                fm_text_tbl_cursor (l_formula_master.text_code) LOOP
1694                l_number_of_text_lines := l_number_of_text_lines + 1;
1695                l_text_table (l_number_of_text_lines).text_code :=
1696                                                  x_batch_header_rec.text_code;
1697                l_text_table (l_number_of_text_lines).line_no :=
1698                                                     l_fm_text_tbl_row.line_no;
1699                l_text_table (l_number_of_text_lines).lang_code :=
1700                                                   l_fm_text_tbl_row.lang_code;
1701                l_text_table (l_number_of_text_lines).paragraph_code :=
1702                                              l_fm_text_tbl_row.paragraph_code;
1703                l_text_table (l_number_of_text_lines).sub_paracode :=
1704                                                l_fm_text_tbl_row.sub_paracode;
1705 
1706                IF l_fm_text_tbl_row.line_no = -1 THEN
1707                   -- Start constructing key field for text code.
1708                   l_text_table (l_number_of_text_lines).text :=
1709                         'gme_batch_header'
1710                      || '|'
1711                      || TO_CHAR (x_batch_header_rec.batch_id)
1712                      || '|';
1713                ELSE
1714                   l_text_table (l_number_of_text_lines).text :=
1715                                                        l_fm_text_tbl_row.text;
1716                END IF;
1717             END LOOP;
1718          END IF;
1719 
1720          --Bug#5112133
1721          IF (g_debug = gme_debug.g_log_statement) THEN
1722           gme_debug.put_line ('l_number_of_formula_lines = '||l_number_of_formula_lines);
1723          END IF;
1724 
1725          FOR l_row_count IN 1 .. l_number_of_formula_lines LOOP
1726             -- Create rows for details' text.
1727             IF (g_debug = gme_debug.g_log_statement) THEN
1728                gme_debug.put_line ('l text code is  '||l_material_details (l_row_count).text_code);
1729             END IF;
1730             IF     l_material_details (l_row_count).text_code IS NOT NULL
1731                AND gme_common_pvt.g_copy_formula_text_ind = 1 THEN
1732                l_text_code := l_material_details (l_row_count).text_code;
1733                l_return :=
1734                   gme_text_dbl.insert_header_row (l_text_header
1735                                                  ,l_text_header);
1736 
1737                IF l_return THEN
1738                   l_material_details (l_row_count).text_code :=
1739                                                       l_text_header.text_code;
1740 
1741                   -- This fetches using the fm text data based on the fm text code.
1742                   FOR l_fm_text_tbl_row IN fm_text_tbl_cursor (l_text_code) LOOP
1743                      l_number_of_text_lines := l_number_of_text_lines + 1;
1744                      l_text_table (l_number_of_text_lines).text_code :=
1745                                                       l_text_header.text_code;
1746                      l_text_table (l_number_of_text_lines).line_no :=
1747                                                     l_fm_text_tbl_row.line_no;
1748                      l_text_table (l_number_of_text_lines).lang_code :=
1749                                                   l_fm_text_tbl_row.lang_code;
1750                      l_text_table (l_number_of_text_lines).paragraph_code :=
1751                                              l_fm_text_tbl_row.paragraph_code;
1752                      l_text_table (l_number_of_text_lines).sub_paracode :=
1753                                                l_fm_text_tbl_row.sub_paracode;
1754 
1755                      IF l_fm_text_tbl_row.line_no = -1 THEN
1756                         -- Start constructing key field for text code.
1757                         l_text_string :=
1758                               'gme_material_details'
1759                            || '|'
1760                            || TO_CHAR
1761                                      (l_material_details (l_row_count).batch_id)
1762                            || '|';
1763                         l_text_string :=
1764                               l_text_string
1765                            || l_material_details (l_row_count).line_type
1766                            || '|';
1767                         l_text_string :=
1768                               l_text_string
1769                            || l_material_details (l_row_count).line_no;
1770                         l_text_table (l_number_of_text_lines).text :=
1771                                                                  l_text_string;
1772                      ELSE
1773                         l_text_table (l_number_of_text_lines).text :=
1774                                                        l_fm_text_tbl_row.text;
1775                      END IF;
1776                   END LOOP;                           -- text lines loop.
1777                ELSE
1778                   -- We could not insert the text header. Panic
1779                   --Bug#5112133
1780                   IF (g_debug = gme_debug.g_log_statement) THEN
1781                    gme_debug.put_line ('Error in inserting text header');
1782                   END IF;
1783                   RAISE expected_error;
1784                END IF;
1785             END IF;
1786 
1787             l_material_details (l_row_count).batch_id :=
1788                                                    x_batch_header_rec.batch_id;
1789 
1790             --FPBug#4395561  Start
1791              l_return_status := NULL;
1792              gme_validate_flex_fld_pvt.create_flex_material_details(
1793                                         l_material_details (l_row_count),
1794                                         l_material_details (l_row_count),
1795                                         l_return_status);
1796              IF l_return_status <> FND_API.g_ret_sts_success THEN
1797                RAISE create_flex_failure;
1798              END IF;
1799              --FPBug#4395561  End
1800              --Pawan  changes for GMO
1801               IF  (l_material_details (l_row_count).line_type  =
1802                   gme_common_pvt.g_line_type_ing )
1803               AND (l_material_details (l_row_count).phantom_type = 0 )
1804               --Pawan Kumar add for bug 5365883
1805               -- Kapil M. Bug# 5458674. Reverted back the changes to support LCF Batches.
1806               -- AND (p_creation_mode <> 'LCF')
1807               THEN
1808 
1809                 GMO_DISPENSE_GRP.IS_DISPENSE_ITEM (p_api_version   => 1.0,
1810                             p_init_msg_list       => fnd_api.g_false ,
1811                             x_return_status       => l_return_status ,
1812                             x_msg_count           => l_message_count ,
1813                             x_msg_data            => l_message_list ,
1814                             p_inventory_item_id   => l_material_details (l_row_count).inventory_item_id,
1815                             p_organization_id     => x_batch_header_rec.organization_id,
1816                             p_recipe_id           => l_recipe.recipe_id,
1817                             x_dispense_required   => l_dispense_required,
1818                             x_dispense_config_id  => l_config_id);
1819 
1820                 IF l_return_status IN ('S', 'W') THEN
1821                     l_material_details (l_row_count).dispense_ind :=  l_dispense_required ;
1822                 END IF;
1823 
1824              END IF;
1825               -- GMO changes end
1826              IF (g_debug = gme_debug.g_log_statement) THEN
1827                gme_debug.put_line ('MATERTIAL lines to be INSERTED ' || l_row_count);
1828             END IF;
1829 
1830             l_return :=
1831                gme_material_details_dbl.insert_row
1832                                             (l_material_details (l_row_count)
1833                                             ,l_material_details (l_row_count) );
1834 
1835             IF (g_debug = gme_debug.g_log_statement) THEN
1836                gme_debug.put_line ('MATERTIAL_INSERTED');
1837             END IF;
1838 
1839             IF NOT l_return THEN
1840                RAISE unexpected_error;
1841             END IF;
1842            -- Pawan Kumar added for bug 4947535
1843 
1844             IF (l_config_id IS NOT NULL AND l_material_details(l_row_count).dispense_ind = 'Y') then
1845               IF (NVL (g_debug, -1) = gme_debug.g_log_statement) THEN
1846                    gme_debug.put_line (g_pkg_name||'.'||l_api_name||'Instantiating  material line id'
1847                     || l_material_details (l_row_count).material_detail_id);
1848                    gme_debug.put_line (g_pkg_name||'.'||l_api_name||' config id ' || l_config_id);
1849               END IF;
1850              GMO_DISPENSE_GRP.INSTANTIATE_DISPENSE_SETUP
1851                         (p_api_version          => 1.0
1852                           ,p_dispense_config_id         => l_config_id
1853                           ,p_entity_name                => GMO_DISPENSE_GRP.G_MATERIAL_LINE_ENTITY
1854                           ,p_entity_key                 => l_material_details(l_row_count).material_detail_id
1855                           ,p_init_msg_list      => FND_API.G_FALSE
1856                           ,x_return_status      => l_return_status
1857                           ,x_msg_count          => l_message_count
1858                           ,x_msg_data           => l_message_list);
1859               IF l_return_status <> FND_API.G_RET_STS_SUCCESS THEN
1860 
1861                RAISE unexpected_error;
1862               END IF;
1863             END IF;
1864 
1865          END LOOP;
1866 
1867          -- Insert Text detail for all the new text codes, which
1868          -- hold the data for all the detail lines and the batch header.
1869          FOR l_row_count IN 1 .. l_text_table.COUNT LOOP
1870             l_return :=
1871                gme_text_dbl.insert_text_row (l_text_table (l_row_count)
1872                                             ,l_text_table (l_row_count) );
1873 
1874             IF NOT l_return THEN
1875                RAISE unexpected_error;
1876             END IF;
1877          END LOOP;
1878       ELSE
1879          RAISE unexpected_error;
1880       END IF;
1881 
1882       -- Bath was created OK, so now try to create the steps (if needed)
1883       /*Restore the dates as supplied by user If user has suppled plan_start_date, it will be used to calculate other two.
1884       If user has supplied plan_cmplt_date and plan_start_date is null then plan_cmplt_date will be used to calculate other 2 dates;  */
1885       x_batch_header_rec.plan_start_date := p_batch_header_rec.plan_start_date;
1886       x_batch_header_rec.plan_cmplt_date := p_batch_header_rec.plan_cmplt_date;
1887       x_batch_header_rec.due_date := p_batch_header_rec.due_date;
1888 
1889       SELECT primary_uom_code
1890         INTO l_prim_item_um
1891         FROM mtl_system_items_b
1892        WHERE inventory_item_id = l_recipe_validity_rule.inventory_item_id
1893          AND organization_id = x_batch_header_rec.organization_id;
1894 
1895       OPEN get_prim_prod (x_batch_header_rec.batch_id
1896                          ,l_recipe_validity_rule.inventory_item_id);
1897 
1898       FETCH get_prim_prod
1899        INTO l_prim_prod_qty, l_prim_prod_um;
1900 
1901       IF get_prim_prod%FOUND THEN
1902          l_prim_prod_found := TRUE;
1903       ELSE
1904          l_prim_prod_found := FALSE;
1905       END IF;
1906 
1907       CLOSE get_prim_prod;
1908 
1909       IF g_debug <= gme_debug.g_log_statement THEN
1910          gme_debug.put_line (   g_pkg_name
1911                              || '.'
1912                              || l_api_name
1913                              || 'Start step processing');
1914       END IF;
1915 
1916       IF gme_common_pvt.routings.COUNT <> 0 THEN
1917          gme_create_step_pvt.create_batch_steps
1918                  (p_recipe_rout_step_tbl      => gme_common_pvt.steps
1919                  ,p_recipe_rout_act_tbl       => gme_common_pvt.activities
1920                  ,p_recipe_rout_resc_tbl      => gme_common_pvt.resources
1921                  ,p_resc_parameters_tbl       => gme_common_pvt.process_parameters
1922                  ,p_recipe_rout_matl_tbl      => gme_common_pvt.routing_materials
1923                  ,p_routing_depd_tbl          => gme_common_pvt.step_dependencies
1924                  ,p_gme_batch_header_rec      => x_batch_header_rec
1925                  ,p_use_workday_cal           => p_use_workday_cal
1926                  ,p_contiguity_override       => p_contiguity_override
1927                  ,p_ignore_qty_below_cap      => p_ignore_qty_below_cap
1928                  ,x_return_status             => x_return_status);
1929 
1930          IF x_return_status <> fnd_api.g_ret_sts_success THEN
1931             RAISE steps_creation_failure;
1932          END IF;
1933 
1934          IF NOT (gme_batch_header_dbl.fetch_row (x_batch_header_rec
1935                                                 ,x_batch_header_rec) ) THEN
1936             RAISE batch_header_fetch_failure;
1937          END IF;
1938       ELSE
1939          /* routing count = 0... there are no steps, so calculate the dates with prod rules if they exist... */
1940          IF l_prim_prod_found THEN
1941             l_temp_qty :=
1942                inv_convert.inv_um_convert
1943                                    (l_recipe_validity_rule.inventory_item_id
1944                                    ,5
1945                                    ,l_prim_prod_qty
1946                                    ,l_prim_prod_um
1947                                    ,l_prim_item_um
1948                                    ,NULL
1949                                    ,NULL);
1950 
1951             IF l_temp_qty < 0 THEN
1952                l_item_id := l_recipe_validity_rule.inventory_item_id;
1953                l_from_uom := l_prim_prod_um;
1954                l_to_uom := l_prim_item_um;
1955                RAISE conversion_failure;
1956             END IF;
1957 
1958             IF (gme_common_pvt.calc_date_from_prod_rule
1959                    (p_organization_id        => x_batch_header_rec.organization_id
1960                    ,p_inventory_item_id      => l_recipe_validity_rule.inventory_item_id
1961                    ,p_item_qty               => l_temp_qty
1962                    ,p_start_date             => x_batch_header_rec.plan_start_date
1963                    ,p_cmplt_date             => x_batch_header_rec.plan_cmplt_date
1964                    ,x_start_date             => x_batch_header_rec.plan_start_date
1965                    ,x_cmplt_date             => x_batch_header_rec.plan_cmplt_date) ) THEN
1966                l_no_prod_rule_found := FALSE;
1967             ELSE
1968                l_no_prod_rule_found := TRUE;
1969             END IF;
1970          ELSE
1971             -- prim prod was not found...
1972             l_no_prod_rule_found := TRUE;
1973          END IF;
1974 
1975          IF l_no_prod_rule_found THEN
1976             IF     x_batch_header_rec.plan_start_date IS NOT NULL
1977                AND x_batch_header_rec.plan_cmplt_date IS NULL THEN
1978                x_batch_header_rec.plan_cmplt_date :=
1979                                            x_batch_header_rec.plan_start_date;
1980             ELSIF     x_batch_header_rec.plan_start_date IS NULL
1981                   AND x_batch_header_rec.plan_cmplt_date IS NOT NULL THEN
1982                x_batch_header_rec.plan_start_date :=
1983                                            x_batch_header_rec.plan_cmplt_date;
1984             ELSIF     x_batch_header_rec.plan_start_date IS NULL
1985                   AND x_batch_header_rec.plan_cmplt_date IS NULL THEN
1986                x_batch_header_rec.plan_start_date :=
1987                                                    gme_common_pvt.g_timestamp;
1988                x_batch_header_rec.plan_cmplt_date :=
1989                                                    gme_common_pvt.g_timestamp;
1990             END IF;
1991 
1992             IF (g_debug = gme_debug.g_log_statement) THEN
1993                gme_debug.put_line
1994                                (   'production rule start_date '
1995                                 || TO_CHAR
1996                                           (x_batch_header_rec.plan_start_date
1997                                           ,'DD-MON-YYYY HH24:MI:SS') );
1998                gme_debug.put_line
1999                                 (   'production rule end_date '
2000                                  || TO_CHAR
2001                                           (x_batch_header_rec.plan_cmplt_date
2002                                           ,'DD-MON-YYYY HH24:MI:SS') );
2003             END IF;
2004          ELSE
2005             IF p_use_workday_cal = fnd_api.g_true THEN
2006                gmd_recipe_fetch_pub.fetch_contiguous_ind
2007                   (p_recipe_id                    => l_recipe_validity_rule.recipe_id
2008                   ,p_orgn_id                      => p_batch_header_rec.organization_id
2009                   ,p_recipe_validity_rule_id      => l_recipe_validity_rule.recipe_validity_rule_id
2010                   ,x_contiguous_ind               => l_cont_ind
2011                   ,x_return_status                => l_return_status);
2012 
2013                IF l_return_status <> fnd_api.g_ret_sts_success THEN
2014                   IF (g_debug = gme_debug.g_log_statement) THEN
2015                      gme_debug.put_line
2016                         (   'GMD_RECIPE_FETCH_PUB.FETCH_CONTIGUOUS_IND returned error '
2017                          || l_return_status);
2018                   END IF;
2019 
2020                   l_cont_ind := 0;
2021                END IF;
2022 
2023                IF (g_debug = gme_debug.g_log_statement) THEN
2024                   gme_debug.put_line (   'Calendar code found '
2025                                       || gme_common_pvt.g_calendar_code);
2026                   gme_debug.put_line ('Cont ID found ' || l_cont_ind);
2027                END IF;
2028 
2029                l_duration :=
2030                     (  x_batch_header_rec.plan_cmplt_date
2031                      - x_batch_header_rec.plan_start_date)
2032                   * 24;
2033 
2034                IF (g_debug = gme_debug.g_log_statement) THEN
2035                   gme_debug.put_line ('l duration ' || l_duration);
2036                END IF;
2037 
2038                IF    p_batch_header_rec.plan_start_date IS NOT NULL
2039                   OR (    p_batch_header_rec.plan_start_date IS NULL
2040                       AND p_batch_header_rec.plan_cmplt_date IS NULL) THEN
2041                   gmp_calendar_api.get_contiguous_periods
2042                      (p_api_version        => 1
2043                      ,p_init_msg_list      => FALSE
2044                      ,p_start_date         => NVL
2045                                                  (p_batch_header_rec.plan_start_date
2046                                                  ,x_batch_header_rec.plan_start_date)
2047                      ,p_end_date           => NULL
2048                      ,p_calendar_code      => gme_common_pvt.g_calendar_code
2049                      ,p_duration           => l_duration
2050                      ,p_output_tbl         => l_contig_period_tbl
2051                      ,x_return_status      => l_return_status);
2052 
2053                   IF (l_return_status <> x_return_status) THEN
2054                      RAISE error_cont_period;
2055                   END IF;
2056 
2057                   l_cal_count := l_contig_period_tbl.COUNT;
2058 
2059                   IF (g_debug = gme_debug.g_log_statement) THEN
2060                      gme_debug.put_line ('l cal_count ' || l_cal_count);
2061                      gme_debug.put_line (   'p_contiguity_override '
2062                                          || p_contiguity_override);
2063                   END IF;
2064 
2065                   IF l_cont_ind = 1
2066                      AND p_contiguity_override = fnd_api.g_false THEN
2067                      IF l_cal_count > 1 THEN
2068                         RAISE error_non_contiguious;
2069                      END IF;
2070                   END IF;
2071 
2072                   x_batch_header_rec.plan_cmplt_date :=
2073                                     l_contig_period_tbl (l_cal_count).end_date;
2074                ELSE
2075                   IF p_batch_header_rec.plan_cmplt_date IS NOT NULL THEN
2076                      gmp_calendar_api.get_contiguous_periods
2077                           (p_api_version        => 1
2078                           ,p_init_msg_list      => FALSE
2079                           ,p_start_date         => NULL
2080                           ,p_end_date           => p_batch_header_rec.plan_cmplt_date
2081                           ,p_calendar_code      => gme_common_pvt.g_calendar_code
2082                           ,p_duration           => l_duration
2083                           ,p_output_tbl         => l_contig_period_tbl
2084                           ,x_return_status      => l_return_status);
2085 
2086                      IF (l_return_status <> x_return_status) THEN
2087                         RAISE error_cont_period;
2088                      END IF;
2089 
2090                      l_cal_count := l_contig_period_tbl.COUNT;
2091 
2092                      IF (g_debug = gme_debug.g_log_statement) THEN
2093                         gme_debug.put_line ('l cal_count ' || l_cal_count);
2094                         gme_debug.put_line (   'p_contiguity_override '
2095                                             || p_contiguity_override);
2096                      END IF;
2097 
2098                      IF     l_cont_ind = 1
2099                         AND p_contiguity_override = fnd_api.g_false THEN
2100                         IF l_cal_count > 1 THEN
2101                            RAISE error_non_contiguious;
2102                         END IF;
2103                      END IF;
2104 
2105                      x_batch_header_rec.plan_start_date :=
2106                                   l_contig_period_tbl (l_cal_count).start_date;
2107                   END IF;
2108                END IF;
2109             END IF;
2110          END IF;
2111 
2112          UPDATE gme_batch_header
2113             SET plan_start_date = x_batch_header_rec.plan_start_date
2114                ,plan_cmplt_date = x_batch_header_rec.plan_cmplt_date
2115                ,due_date =
2116                    NVL (x_batch_header_rec.due_date
2117                        ,x_batch_header_rec.plan_cmplt_date)
2118                -- Bug 13256866
2119                ,last_updated_by = gme_common_pvt.g_user_ident
2120                ,last_update_date = gme_common_pvt.g_timestamp
2121                ,last_update_login = gme_common_pvt.g_login_id
2122           WHERE batch_id = x_batch_header_rec.batch_id;
2123       END IF;
2124 
2125          -- 5698727
2126          l_in_batch_header1 := x_batch_header_rec ;
2127          gme_common_pvt.create_document_no (l_in_batch_header1
2128                                            ,x_batch_header_rec);
2129          -- 5698727 rework
2130          /*Bug#6398619 the validation here is required only for the automatic doc numbering */
2131         IF l_doc_numbering = gme_common_pvt.g_auto_doc_numbering THEN
2132 
2133            -- Bug 13785754/13815190 - try 20 times if necessary to get a unique batch number.
2134            l_doc_count := 1;
2135            WHILE l_doc_count < 20 LOOP
2136 
2137               validate_wip_entity(p_organization_id => x_batch_header_rec.organization_id,
2138                                   p_batch_no        => l_prefix||x_batch_header_rec.batch_no,
2139                                   x_return_status   => l_return_status);
2140 
2141               IF l_return_status <> fnd_api.g_ret_sts_success THEN
2142                  IF l_doc_count > 18 THEN
2143                     RAISE wip_entity_err;
2144                  ELSE
2145                     l_doc_count := l_doc_count + 1;
2146                     gme_common_pvt.create_document_no (l_in_batch_header1
2147                                                       ,x_batch_header_rec);
2148                  END IF;
2149               ELSE
2150                  -- Force loop to stop.
2151                  l_doc_count := 99;
2152               END IF;
2153            END LOOP;
2154 
2155            /* update the batch_no with the actual value */
2156            UPDATE gme_batch_header
2157               SET batch_no = x_batch_header_rec.batch_no
2158 	         -- Bug 13256866
2159 	         ,last_updated_by = gme_common_pvt.g_user_ident
2160 	         ,last_update_date = gme_common_pvt.g_timestamp
2161 	         ,last_update_login = gme_common_pvt.g_login_id
2162             WHERE batch_id = x_batch_header_rec.batch_id;
2163 
2164            /*5698727 rework update the wip_entities table with actual batch no*/
2165            UPDATE wip_entities
2166               SET wip_entity_name = l_prefix||x_batch_header_rec.batch_no
2167             WHERE organization_id = x_batch_header_rec.organization_id
2168               AND wip_entity_name = l_prefix||l_doc_timestamp;
2169         END IF;
2170         -- 5698727
2171 
2172       IF (g_debug = gme_debug.g_log_statement) THEN
2173          gme_debug.put_line (   'Calculated Start date is '
2174                              || TO_CHAR (x_batch_header_rec.plan_start_date
2175                                         ,'DD-MON-YYYY HH24:MI:SS') );
2176          gme_debug.put_line (   'Calculated Cmplt date is '
2177                              || TO_CHAR (x_batch_header_rec.plan_cmplt_date
2178                                         ,'DD-MON-YYYY HH24:MI:SS') );
2179       END IF;
2180 
2181       IF (    p_batch_header_rec.plan_start_date IS NOT NULL
2182           AND p_batch_header_rec.plan_cmplt_date IS NOT NULL) THEN
2183          -- IF routings exists and calculated date is greater than the date entered,
2184          -- then truncate all the dates to dates entered
2185          IF (gme_common_pvt.routings.COUNT <> 0) THEN
2186             IF (x_batch_header_rec.plan_cmplt_date >
2187                                             p_batch_header_rec.plan_cmplt_date) THEN
2188                x_batch_header_rec.plan_start_date :=
2189                                            p_batch_header_rec.plan_start_date;
2190                x_batch_header_rec.plan_cmplt_date :=
2191                                            p_batch_header_rec.plan_cmplt_date;
2192                gme_reschedule_batch_pvt.truncate_date
2193                                    (p_batch_header_rec      => x_batch_header_rec
2194                                    ,p_date                  => 1
2195                                    ,p_batchstep_id          => NULL
2196                                    ,x_return_status         => l_return_status);
2197 
2198                IF l_return_status <> x_return_status THEN
2199                   RAISE error_truncate_date;
2200                END IF;
2201             -- Routings exists and calculated date is less than date entered,
2202             -- then updates the dates as entered by the user.
2203             ELSE
2204                UPDATE gme_batch_header
2205                   SET plan_cmplt_date = p_batch_header_rec.plan_cmplt_date
2206                      ,due_date =
2207                          NVL (x_batch_header_rec.due_date
2208                              ,p_batch_header_rec.plan_cmplt_date)
2209                      ,last_updated_by = gme_common_pvt.g_user_ident
2210                      ,last_update_date = gme_common_pvt.g_timestamp
2211                      ,last_update_login = gme_common_pvt.g_login_id
2212                 WHERE batch_id = x_batch_header_rec.batch_id;
2213             END IF;
2214          END IF;                    -- End gme_common_pvt.routings.COUNT  <> 0
2215 
2216          UPDATE gme_batch_header
2217             SET plan_cmplt_date = p_batch_header_rec.plan_cmplt_date
2218                ,due_date =
2219                    NVL (x_batch_header_rec.due_date
2220                        ,p_batch_header_rec.plan_cmplt_date)
2221                ,last_updated_by = gme_common_pvt.g_user_ident
2222                ,last_update_date = gme_common_pvt.g_timestamp
2223                ,last_update_login = gme_common_pvt.g_login_id
2224           WHERE batch_id = x_batch_header_rec.batch_id;
2225       END IF;                      -- End start and completion dates not null.
2226 
2227       IF NOT (gme_batch_header_dbl.fetch_row (x_batch_header_rec
2228                                              ,x_batch_header_rec) ) THEN
2229          RAISE batch_header_fetch_failure;
2230       END IF;
2231 
2232       IF g_debug <= gme_debug.g_log_statement THEN
2233          gme_debug.put_line (   g_pkg_name
2234                              || '.'
2235                              || l_api_name
2236                              || 'Calculate mtl req date');
2237       END IF;
2238 
2239       l_item_substituted := FALSE;
2240       FOR l_row_count IN 1 .. l_number_of_formula_lines LOOP
2241          gme_common_pvt.calc_mtl_req_date
2242             (p_batch_header_rec      => x_batch_header_rec
2243             ,p_batchstep_rec         => NULL
2244             ,p_mtl_dtl_rec           => l_material_details (l_row_count)
2245             ,x_mtl_req_date          => l_material_details (l_row_count).material_requirement_date
2246             ,x_return_status         => l_return_status);
2247 
2248          IF (l_return_status <> fnd_api.g_ret_sts_success) THEN
2249             RAISE calc_mtl_req_date_err;
2250          ELSE
2251             --FPBug#4351032 Start
2252             /*Material requirement date is in our hands we need to find out whether particular ingredient
2253                is effective or not depending on substitution list defined
2254             */
2255             l_curr_item_substituted := FALSE;
2256             IF l_material_details (l_row_count).phantom_type = 0 AND
2257                l_material_details (l_row_count).line_type = -1 THEN
2258 
2259                -- nsinghi bug#5674398
2260                -- Pass the ingredient substitution date rather than the material requirement date.
2261                -- At this point, steps table is not updated. Hence need to have similar logic here too
2262                -- as in gme_api_grp.get_ingr_sub_date.
2263 
2264                IF gme_common_pvt.g_ingr_sub_date = 2 THEN
2265                  l_ingred_req_date := l_material_details (l_row_count).material_requirement_date;
2266                ELSIF gme_common_pvt.g_ingr_sub_date = 1 THEN
2267                  l_ingred_req_date := NVL(p_batch_header_rec.plan_start_date, x_batch_header_rec.plan_start_date);
2268                ELSIF gme_common_pvt.g_ingr_sub_date = 3 THEN
2269                  l_ingred_req_date := NVL(p_batch_header_rec.plan_cmplt_date, x_batch_header_rec.plan_cmplt_date);
2270                END IF;
2271 
2272                IF g_debug <= gme_debug.g_log_statement THEN
2273                   gme_debug.put_line (   g_pkg_name||'.'|| l_api_name
2274                                       || ' l_ingred_req_date '||TO_CHAR(l_ingred_req_date, 'MON-DD-YYYY HH24:MI:SS'));
2275                END IF;
2276 
2277                gmdfmval_pub.get_substitute_line_item (
2278                        pformulaline_id        => l_material_details (l_row_count).formulaline_id,
2279                        pitem_id               => l_material_details (l_row_count).inventory_item_id,
2280                        pqty                   => l_material_details (l_row_count).plan_qty,
2281                        puom                   => l_material_details (l_row_count).dtl_um,
2282                        pscale_multiple        => l_material_details (l_row_count).scale_multiple,
2283 -- nsinghi bug#5674398. Pass the ingredient substitution date rather than the material requirement date
2284 --                       pdate                  => l_material_details (l_row_count).material_requirement_date,
2285                        pdate                  => l_ingred_req_date,
2286                        xformuladetail_tbl     => l_formula_tbl);
2287 
2288                IF l_material_details (l_row_count).inventory_item_id <> l_formula_tbl(1).inventory_item_id THEN
2289 
2290                  -- Bug 11815699 - get item status code.
2291                  -- Bug 7578476 - Fetch primary uom code also.
2292                  -- Remove redundant cursor introduced by 4917631
2293                  OPEN  item_master_cursor (l_formula_tbl(1).inventory_item_id
2294                                          ,x_batch_header_rec.organization_id);
2295                  FETCH item_master_cursor
2296                  INTO  l_new_item_rec.inventory_item_id, l_new_item_rec.concatenated_segments,
2297                        l_new_item_rec.eng_item_flag, l_new_item_rec.process_execution_enabled_flag,
2298                        l_new_item_rec.primary_uom_code, l_item_master.inventory_item_status_code;
2299 
2300                  CLOSE item_master_cursor;
2301 
2302                  /* check whether item is process execution enabled and it's not experimental item incase of lab batches */
2303                   IF l_new_item_rec.PROCESS_EXECUTION_ENABLED_FLAG <> 'Y' OR
2304                      ( l_new_item_rec.ENG_ITEM_FLAG = 'Y' AND NVL(x_batch_header_rec.laboratory_ind,0) <> 1 ) THEN
2305                     RAISE invalid_item_substitute;
2306                   END IF;
2307 
2308                   IF (g_debug <= gme_debug.g_log_statement) THEN
2309                    gme_debug.put_line('Calculated mtl req date: '||l_material_details (l_row_count).material_requirement_date);
2310                    gme_debug.put_line('Initial Item ID: '||l_material_details (l_row_count).inventory_item_id);
2311                    gme_debug.put_line('Initial Plan Qty: '||l_material_details (l_row_count).plan_qty);
2312                    gme_debug.put_line('Initial Detail UOM: '||l_material_details (l_row_count).dtl_um);
2313                    gme_debug.put_line('Initial Scale multiple: '||l_material_details (l_row_count).scale_multiple);
2314                   END IF;
2315 
2316                   l_item_substituted := TRUE;
2317                   l_curr_item_substituted := TRUE;
2318 
2319                   /*reassign new item values to material details */
2320                   l_material_details (l_row_count).inventory_item_id := l_formula_tbl(1).inventory_item_id;
2321                   l_material_details (l_row_count).plan_qty := l_formula_tbl(1).qty;
2322                   l_material_details (l_row_count).original_qty := l_formula_tbl(1).qty;
2323                   l_material_details (l_row_count).dtl_um := l_formula_tbl(1).detail_uom;
2324                   l_material_details (l_row_count).scale_multiple := l_formula_tbl(1).scale_multiple;
2325 
2326                   IF (g_debug <= gme_debug.g_log_statement) THEN
2327                    gme_debug.put_line('Substitued Item ID: '||l_formula_tbl(1).inventory_item_id);
2328                    gme_debug.put_line('Substitued Plan Qty: '||l_formula_tbl(1).qty);
2329                    gme_debug.put_line('Substituted Detail UOM: '||l_formula_tbl(1).detail_uom);
2330                    gme_debug.put_line('Substituted Scale multiple: '||l_formula_tbl(1).scale_multiple);
2331                   END IF;
2332 
2333                   /*if the new item uom is not the primary uom then calculate the primary quantity*/
2334                   IF l_formula_tbl(1).detail_uom <> l_new_item_rec.primary_uom_code THEN
2335                     l_temp_qty := inv_convert.inv_um_convert
2336                                       (item_id       => l_material_details(l_row_count).inventory_item_id
2337                                       ,precision     => 5
2338                                       ,from_quantity => l_material_details(l_row_count).plan_qty
2339                                       ,from_unit     => l_material_details(l_row_count).dtl_um
2340                                       ,to_unit       => l_new_item_rec.primary_uom_code
2341                                       ,from_name     => NULL
2342                                       ,to_name       => NULL);
2343                   ELSE
2344                     l_temp_qty := l_material_details(l_row_count).plan_qty;
2345                   END IF;
2346 
2347                   IF (g_debug < gme_debug.g_log_statement) THEN
2348                    gme_debug.put_line('Initial Original Primary Qty: '||l_material_details (l_row_count).original_primary_qty);
2349                    gme_debug.put_line('Substituted Original Priamry Qty: '||l_temp_qty);
2350                   END IF;
2351 
2352                   /* assign to original primary qty */
2353                   l_material_details (l_row_count).original_primary_qty := l_temp_qty;
2354                ELSE
2355                   l_curr_item_substituted := FALSE;
2356                END IF; /* item id check */
2357             END IF;  /* phantom type and line type check */
2358              --FPBug#4351032 End
2359 
2360             -- Bug 7710435 - Added p_called_by parameter.
2361             l_return :=
2362                 gme_material_details_dbl.update_row (p_material_detail => l_material_details (l_row_count),
2363                                                      p_called_by =>'C' );
2364 
2365             /* FPBug#4351032 Updating original primary qty field manually
2366                as this update is not allowed in above dbl procedure */
2367 
2368             UPDATE gme_material_details
2369                SET original_primary_qty = l_material_details (l_row_count).original_primary_qty
2370              WHERE material_detail_id = l_material_details (l_row_count).material_detail_id;
2371 
2372             -- nsinghi bug#5674398
2373             -- if ASQC is on and current material line has been substitued, recalculate step qtys
2374             IF x_batch_header_rec.automatic_step_calculation = 1 AND l_curr_item_substituted THEN
2375                OPEN c_batchsteps (l_material_details(l_row_count).material_detail_id);
2376                FETCH c_batchsteps INTO l_batchstep_rec;
2377                CLOSE c_batchsteps;
2378 
2379                IF (g_debug <= gme_debug.g_log_statement) THEN
2380                  gme_debug.put_line ('Before updating step qty after the substitution');
2381                END IF;
2382                gme_update_step_qty_pvt.update_step_qty (p_batch_step_rec  => l_batchstep_rec,
2383                                                       x_message_count     => l_message_count,
2384                                                       x_message_list      => l_message_list,
2385                                                       x_return_status     => x_return_status,
2386                                                       x_batch_step_rec    => x_batchstep_rec
2387                                                      );
2388                IF (g_debug <= gme_debug.g_log_statement) THEN
2389                  gme_debug.put_line ('After update step qty, return status is:' || x_return_status);
2390                END IF;
2391                IF x_return_status <> fnd_api.g_ret_sts_success THEN
2392                  -- We could not update the step qty
2393                   RAISE unexpected_error;
2394                END IF;
2395             END IF;
2396          END IF;
2397       END LOOP;
2398 
2399       -- nsinghi bug#5674398 START
2400       -- If atleast one item is substituted and the batch is ASQC batch
2401       -- then we will recalculate the start and end dates by calling reschedule batch
2402       IF NVL (x_batch_header_rec.update_inventory_ind, 'Y') = 'Y' AND l_item_substituted = TRUE THEN
2403          IF x_batch_header_rec.automatic_step_calculation = 1 THEN
2404             /* Assigning the user passed dates so that batch gets rescheduled to the passed dates*/
2405 
2406             -- Restore the dates as supplied by user. If user does not provide either start or cmplt dt, use
2407             -- newly created batch's planned start date to re-schedule.
2408             IF p_batch_header_rec.plan_start_date IS NULL AND p_batch_header_rec.plan_cmplt_date IS NULL THEN
2409               x_batch_header_rec.plan_cmplt_date := p_batch_header_rec.plan_cmplt_date;
2410             ELSE
2411               x_batch_header_rec.plan_start_date := p_batch_header_rec.plan_start_date;
2412               x_batch_header_rec.plan_cmplt_date := p_batch_header_rec.plan_cmplt_date;
2413             END IF;
2414 
2415             l_batch_header_rec := x_batch_header_rec;
2416             gme_reschedule_batch_pvt.reschedule_batch (
2417                  p_batch_header_rec     => l_batch_header_rec,
2418                  p_use_workday_cal      => p_use_workday_cal,
2419                  p_contiguity_override  => p_contiguity_override,
2420                  x_batch_header_rec     => x_batch_header_rec,
2421                  x_return_status        => x_return_status
2422                  );
2423 
2424             IF (g_debug <= gme_debug.g_log_statement) THEN
2425                gme_debug.put_line('Batch Planned Start Date '||TO_CHAR(x_batch_header_rec.plan_start_date,'MON-DD-YYYY HH24:MI:SS'));
2426                gme_debug.put_line('Batch Planned Completion Date '||TO_CHAR(x_batch_header_rec.plan_cmplt_date,'MON-DD-YYYY HH24:MI:SS'));
2427             END IF;
2428 
2429             IF x_return_status <> FND_API.G_RET_STS_SUCCESS THEN
2430                RAISE unexpected_error;
2431             END IF; /* Reschedule of the batch to the user passed dates */
2432 
2433             /* nsinghi bug#5674398 Added the FETCH condition. Reschedule_batch will update the
2434             material_requirement_date, hence requery material detail records */
2435 
2436             l_in_material_detail.batch_id := x_batch_header_rec.batch_id;
2437             IF NOT gme_material_details_dbl.fetch_tab(l_in_material_detail, l_material_details) THEN
2438               RAISE material_dtl_fetch_failure;
2439             END IF;
2440             UPDATE gme_batch_header
2441                SET due_date =
2442                    x_batch_header_rec.plan_cmplt_date
2443                   ,last_updated_by = gme_common_pvt.g_user_ident
2444                   ,last_update_date = gme_common_pvt.g_timestamp
2445                   ,last_update_login = gme_common_pvt.g_login_id
2446              WHERE batch_id = x_batch_header_rec.batch_id;
2447 
2448          END IF;   /* ASQC */
2449       END IF; /* Update inventory*/
2450       -- nsinghi bug#5674398 END
2451 
2452       IF (g_debug = gme_debug.g_log_statement) THEN
2453          gme_debug.put_line ('p_creation_mode=' || p_creation_mode);
2454          gme_debug.put_line ('prim_prod_qty=' || l_prim_prod_qty);
2455          gme_debug.put_line ('prim_prod_um=' || l_prim_prod_um);
2456          gme_debug.put_line ('p_batch_size=' || p_batch_size);
2457          gme_debug.put_line ('p_batch_size_uom=' || p_batch_size_uom);
2458          gme_debug.put_line (   'User passed Start date is '
2459                              || TO_CHAR (p_batch_header_rec.plan_start_date
2460                                         ,'DD-MON-YYYY HH24:MI:SS') );
2461          gme_debug.put_line (   'User passed Cmplt date is '
2462                              || TO_CHAR (p_batch_header_rec.plan_cmplt_date
2463                                         ,'DD-MON-YYYY HH24:MI:SS') );
2464       END IF;
2465 
2466       IF l_prim_prod_found AND (p_creation_mode = 'PRODUCT') THEN
2467          -- Bug 7565054 - Add paramater p_sum_all_prod_lines to cursor to control summation.
2468          OPEN cur_batch_qty (x_batch_header_rec.batch_id
2469                             ,l_recipe_validity_rule.inventory_item_id
2470                             ,p_sum_all_prod_lines);
2471 
2472          FETCH cur_batch_qty
2473           INTO l_temp_qty, l_temp_line_no;
2474 
2475          CLOSE cur_batch_qty;
2476 
2477          IF l_temp_qty < 0 THEN
2478             l_item_id := l_recipe_validity_rule.inventory_item_id;
2479             l_from_uom := p_batch_size_uom;
2480             l_to_uom := l_prim_prod_um;
2481             RAISE conversion_failure;
2482          END IF;
2483 
2484          IF (g_debug = gme_debug.g_log_statement) THEN
2485             gme_debug.put_line ('requested qty in dtl uom=' || l_temp_qty);
2486             gme_debug.put_line ('requested qty in dtl uom rounded=' || round(l_temp_qty, 4));
2487          END IF;
2488 
2489          --sunitha bug # 5484529 Convert the p_batch_size(user entered product plan quantity
2490          --to the Routing uom and then Compare it with the l_temp_qty.
2491 
2492          -- Bug 6665602 Back out 5484529... Reinstate original condition.
2493          -- Bug 10086349 - Use precision of 4 to make comparison.
2494 
2495          -- Bug 10379034 - Change the comparison so we do not rely on potential rounding issues.
2496          -- If the batch is 99.9 % of what was requested then let it go thru.
2497          -- This is a rework of 10086349. Note: l_temp_qty is already in p_batch_size_uom.
2498 
2499          -- Bug 12909216 - Avoid divide by sero error when qty is zero. This will allow
2500          -- zero qty phantom batches to be created.
2501          IF l_temp_qty <> 0 THEN
2502             IF ((p_batch_size / l_temp_qty) < .999 ) THEN
2503             -- IF (ROUND (p_batch_size, 4) <> ROUND (l_temp_qty, 4) ) THEN
2504             /* IF (ROUND (inv_convert.inv_um_convert (l_recipe_validity_rule.inventory_item_id
2505                                                 ,5
2506                                                 ,p_batch_size
2507                                                 ,p_batch_size_uom
2508                                                 ,l_recipe_validity_rule.detail_uom
2509                                                 ,NULL
2510                                                 ,NULL), 5) <> ROUND (l_temp_qty, 5) ) THEN */
2511 
2512                IF (g_debug = gme_debug.g_log_statement) THEN
2513                   gme_debug.put_line('Batch failed to be created for qty requested with creation by product qty');
2514                END IF;
2515 
2516                RAISE create_by_product_failure;
2517             END IF;
2518          END IF;
2519       ELSIF NOT l_prim_prod_found THEN
2520          IF (g_debug = gme_debug.g_log_statement) THEN
2521             gme_debug.put_line ('I could not find the prim product');
2522          END IF;
2523       END IF;
2524 
2525       IF (g_debug = gme_debug.g_log_statement) THEN
2526          gme_debug.put_line ('Checking dates against validity rule');
2527       END IF;
2528 
2529       IF p_creation_mode <> 'LCF' THEN
2530          IF (NOT gme_common_pvt.check_validity_rule_dates
2531                               (l_recipe_validity_rule.recipe_validity_rule_id
2532                               ,x_batch_header_rec.plan_start_date
2533                               ,x_batch_header_rec.plan_cmplt_date) ) THEN
2534             x_return_status := fnd_api.g_ret_sts_error;
2535             RAISE date_exceed_validity_rule;
2536          END IF;
2537       END IF;                           /* IF p_creation_mode <> 'LCF' THEN */
2538 
2539       IF (g_debug = gme_debug.g_log_statement) THEN
2540          gme_debug.put_line (   'BATCH CREATED, ID = '
2541                              || TO_CHAR (x_batch_header_rec.batch_id) );
2542       END IF;
2543 
2544       /* Update WIP entity table to put the primary product id */
2545       UPDATE wip_entities
2546          SET primary_item_id = l_recipe_validity_rule.inventory_item_id
2547        WHERE wip_entity_id = x_batch_header_rec.batch_id;
2548 
2549      -- Rajesh Patangya Bug # 6752637
2550       /* Now its time to calculate the MTQ for steps based on the product */
2551       IF gme_common_pvt.routings.COUNT <> 0 THEN
2552          IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
2553          gme_debug.put_line (   g_pkg_name
2554                              || '.'
2555                              || l_api_name
2556                              || 'Calling Update_step_mtq');
2557          END IF;
2558 
2559          IF NOT update_step_mtq (x_batch_header_rec.batch_id ) THEN
2560             RAISE update_step_mtq_failure;
2561          END IF;
2562       END IF;
2563 
2564       IF g_debug <= gme_debug.g_log_statement THEN
2565          gme_debug.put_line (   g_pkg_name
2566                              || '.'
2567                              || l_api_name
2568                              || 'Start phantom processing');
2569       END IF;
2570 
2571       /* Now its time to create the phantom batch based on the setting of the phantom type - Automatic */
2572       l_error_count := fnd_msg_pub.count_msg;
2573 
2574       FOR l_row_count IN 1 .. l_number_of_formula_lines LOOP
2575          /* If it is set as an automatic phantom */
2576          IF     l_material_details (l_row_count).phantom_type = 1
2577             AND l_material_details (l_row_count).line_type = -1
2578             AND l_doc_numbering <> 1 THEN
2579             l_material_details_in := l_material_details (l_row_count);
2580 
2581 -- nsinghi bug#5200395. Changed out var for x_exception_material_tbl to l_phantom_exc_material_tbl_out
2582 -- from x_exception_material_tbl
2583             /* Bug 5512352 If creating phantom from here no need to do shortage check since
2584                now get_batch_shortages will do it for phantom batches also */
2585             g_no_phant_short_check := 1;
2586 
2587             -- Bug 7830838 - Use the same value from the parent batch so that FPL
2588             -- gets properly applied or not applied based on user settings.
2589             l_gme_batch_header.fixed_process_loss_applied := p_batch_header_rec.fixed_process_loss_applied;
2590             gme_phantom_pvt.create_phantom
2591                    (p_material_detail_rec         => l_material_details_in
2592                    ,p_batch_header_rec            => l_gme_batch_header --would be nul in this case
2593                    ,x_material_detail_rec         => l_material_details
2594                                                                   (l_row_count)
2595                    ,p_validity_rule_id            => NULL
2596                    ,p_use_workday_cal             => p_use_workday_cal
2597                    ,p_contiguity_override         => p_contiguity_override
2598                    ,p_use_least_cost_validity_rule => p_use_least_cost_validity_rule
2599                    ,x_exception_material_tbl      => l_phantom_exc_material_tbl_out
2600                    ,x_return_status               => l_return_status);
2601             l_error_count_after := fnd_msg_pub.count_msg;
2602             g_no_phant_short_check := 0;
2603             -- nsinghi bug#5200395. This will add the exceptions generated by each phantom ingredient to l_phantom_exc_material_tbl.
2604             /* Bug 5512352 No need to add structure since phantoms are now adone along with main batch */
2605             /*
2606             IF (l_phantom_exc_material_tbl_out.COUNT) > 0 THEN
2607               l_excp_tbl_ptr := NVL(l_phantom_exc_material_tbl.LAST,0);
2608               FOR l_phntm_exc_cnt IN l_phantom_exc_material_tbl_out.FIRST..l_phantom_exc_material_tbl_out.LAST
2609               LOOP
2610                 l_phantom_exc_material_tbl(l_excp_tbl_ptr + l_phntm_exc_cnt) := l_phantom_exc_material_tbl_out(l_phntm_exc_cnt);
2611               END LOOP;
2612             END IF;
2613             */
2614 
2615             IF l_error_count < l_error_count_after THEN
2616                WHILE l_error_count_after > l_error_count LOOP
2617                   fnd_msg_pub.delete_msg (p_msg_index      => l_error_count_after);
2618                   l_error_count_after := l_error_count_after - 1;
2619                END LOOP;
2620             END IF;                  /* l_error_count < l_error_count_after */
2621          END IF;        /* l_material_details(l_row_count).phantom_type = 1 */
2622       END LOOP;            /* l_row_count IN 1 .. l_number_of_formula_lines */
2623 
2624 
2625       -- Bug 7265006 - Moved g_no_phant_short_check to shortage check condition as it was originally intended
2626       -- for shortage checking only. Unfortunately it stopped all the other logic for phantom batches.
2627       -- Now invisible move orders and high level reservations will get created for phantom batches.
2628       IF x_batch_header_rec.batch_type = 0 AND NVL (x_batch_header_rec.update_inventory_ind, 'Y') = 'Y' THEN
2629          /* Check inventory shortages */
2630          IF (gme_common_pvt.g_check_shortages_ind = 1 AND g_no_phant_short_check = 0) THEN
2631             IF g_debug <= gme_debug.g_log_statement THEN
2632                gme_debug.put_line (   g_pkg_name || '.'|| l_api_name|| ' Calling shortages ');
2633              END IF;
2634             gme_common_pvt.get_batch_shortages
2635                      (p_organization_id      => x_batch_header_rec.organization_id
2636                      ,p_batch_id             => x_batch_header_rec.batch_id
2637                      ,p_invoke_mode          => 'O'
2638                      ,p_tree_mode            => gme_common_pvt.g_tree_reservation_mode
2639                      ,x_return_status        => l_return_status
2640                      ,x_exception_tbl        => x_exception_material_tbl);
2641             IF l_return_status <> fnd_api.g_ret_sts_success THEN
2642                RAISE inventory_shortage;
2643             END IF;
2644             -- nsinghi Add the material exceptions from phantom batch to Parent Batch
2645             /*
2646             IF (l_phantom_exc_material_tbl.COUNT) > 0 THEN
2647               l_excp_tbl_ptr := NVL(x_exception_material_tbl.LAST,0);
2648               FOR l_phntm_exc_cnt IN l_phantom_exc_material_tbl.FIRST..l_phantom_exc_material_tbl.LAST
2649               LOOP
2650                 x_exception_material_tbl(l_excp_tbl_ptr + l_phntm_exc_cnt) := l_phantom_exc_material_tbl(l_phntm_exc_cnt);
2651               END LOOP;
2652             END IF;
2653             */
2654             IF (x_exception_material_tbl.COUNT > 0) THEN
2655                x_return_status := gme_common_pvt.g_inv_short_err;
2656             END IF;
2657          END IF;
2658 
2659          /* Create invisible move order */
2660          IF g_debug <= gme_debug.g_log_statement THEN
2661             gme_debug.put_line (   g_pkg_name|| '.'|| l_api_name|| ' Creating Invisible Move Order ');
2662          END IF;
2663 
2664          gme_move_orders_pvt.create_move_order_hdr
2665             (p_organization_id           => x_batch_header_rec.organization_id
2666             ,p_move_order_type           => gme_common_pvt.g_invis_move_order_type
2667             ,x_move_order_header_id      => x_batch_header_rec.move_order_header_id
2668             ,x_return_status             => l_return_status);
2669 
2670          IF g_debug <= gme_debug.g_log_statement THEN
2671             gme_debug.put_line (   g_pkg_name|| '.'|| l_api_name|| 'Invisible Move Order is Created');
2672          END IF;
2673 
2674          IF (l_return_status <> fnd_api.g_ret_sts_success) THEN
2675             RAISE create_mo_hdr_err;
2676          ELSE
2677             IF g_debug <= gme_debug.g_log_statement THEN
2678                gme_debug.put_line (   g_pkg_name|| '.'|| l_api_name|| ' Creating Invisible Move Order Lines');
2679             END IF;
2680 
2681             l_in_material_details := l_material_details;
2682             gme_move_orders_pvt.create_move_order_lines
2683                (p_move_order_header_id      => x_batch_header_rec.move_order_header_id
2684                ,p_move_order_type           => gme_common_pvt.g_invis_move_order_type
2685                ,p_material_details_tbl      => l_in_material_details
2686                ,x_material_details_tbl      => l_material_details
2687                ,x_trolin_tbl                => l_trolin_tbl
2688                ,x_return_status             => l_return_status);
2689 
2690             IF (l_return_status <> fnd_api.g_ret_sts_success) THEN
2691                RAISE create_mo_line_err;
2692             END IF;
2693 
2694             IF g_debug <= gme_debug.g_log_statement THEN
2695                gme_debug.put_line (   g_pkg_name|| '.'|| l_api_name|| 'Invisible Move Order Lines is Created');
2696             END IF;
2697          END IF;
2698 
2699          /* Update batch header with move_order_header_id */
2700          UPDATE gme_batch_header
2701             SET move_order_header_id = x_batch_header_rec.move_order_header_id
2702 	        -- Bug 13256866
2703 	        ,last_updated_by = gme_common_pvt.g_user_ident
2704 	        ,last_update_date = gme_common_pvt.g_timestamp
2705 	        ,last_update_login = gme_common_pvt.g_login_id
2706           WHERE batch_id = x_batch_header_rec.batch_id;
2707 
2708          /* Update material details table we have computed material requirement date and move_order_line_id */
2709          FOR i IN 1 .. l_material_details.COUNT LOOP
2710             -- Bug 7710435 - Added p_called_by parameter.
2711             l_return :=
2712                 gme_material_details_dbl.update_row (p_material_detail => l_material_details (i),
2713                                                      p_called_by =>'C' );
2714          END LOOP;
2715 
2716          -- Bug 7710435  - Let's refetch the detail row since the data has been updated.
2717          l_in_material_detail.batch_id := x_batch_header_rec.batch_id;
2718          IF NOT gme_material_details_dbl.fetch_tab(l_in_material_detail, l_material_details) THEN
2719             RAISE material_dtl_fetch_failure;
2720          END IF;
2721 
2722          /* Create High Level Reservations */
2723          IF (gme_common_pvt.g_create_high_level_resv_ind = 1) THEN
2724             IF g_debug <= gme_debug.g_log_statement THEN
2725                gme_debug.put_line (   g_pkg_name|| '.'|| l_api_name|| ' Creating reservations for batch id '|| x_batch_header_rec.batch_id);
2726             END IF;
2727 
2728             gme_reservations_pvt.create_batch_reservations
2729                        (p_batch_id           => x_batch_header_rec.batch_id
2730                        ,p_timefence          => gme_common_pvt.g_reservation_timefence
2731                        ,x_return_status      => l_return_status);
2732 
2733             IF g_debug <= gme_debug.g_log_statement THEN
2734                gme_debug.put_line (   g_pkg_name
2735                                    || '.'
2736                                    || l_api_name
2737                                    || ' Reservations are created'
2738                                    || l_return_status);
2739             END IF;
2740          END IF;
2741 
2742          /* Create Move Order */
2743          IF (gme_common_pvt.g_create_move_orders_ind = 1) THEN
2744             IF g_debug <= gme_debug.g_log_statement THEN
2745                gme_debug.put_line (   g_pkg_name
2746                                    || '.'
2747                                    || l_api_name
2748                                    || ' Creating Explicit Move Order ');
2749             END IF;
2750 
2751             gme_move_orders_pvt.create_batch_move_order
2752                                 (p_batch_header_rec          => x_batch_header_rec
2753                                 ,p_material_details_tbl      => l_material_details
2754                                 ,x_return_status             => l_return_status);
2755 
2756             IF g_debug <= gme_debug.g_log_statement THEN
2757                gme_debug.put_line (   g_pkg_name
2758                                    || '.'
2759                                    || l_api_name
2760                                    || ' Explicit Move Order are created '
2761                                    || l_return_status);
2762             END IF;
2763          END IF;
2764       END IF;
2765         -- Pawan added code for populating the GMO
2766         IF x_batch_header_rec.enhanced_pi_ind = 'Y' THEN
2767           gmo_vbatch_grp.instantiate_advanced_pi
2768                                  (P_API_VERSION => 1.0,
2769                                   P_INIT_MSG_LIST => FND_API.G_FALSE,
2770                                    P_COMMIT => FND_API.G_FALSE,
2771                                    P_VALIDATION_LEVEL => FND_API.G_VALID_LEVEL_FULL,
2772                                    X_RETURN_STATUS => l_return_status,
2773                                    X_MSG_COUNT => l_message_count,
2774                                    X_MSG_DATA => l_msg_data,
2775                                    P_ENTITY_NAME => 'BATCH',
2776                                    P_ENTITY_KEY => x_batch_header_rec.batch_id) ;
2777            IF g_debug <= gme_debug.g_log_statement THEN
2778                gme_debug.put_line (   g_pkg_name
2779                                    || '.'
2780                                    || l_api_name
2781                                    || ' Calling instantiate_advanced_pi ');
2782             END IF;
2783            IF l_return_status <> fnd_api.g_ret_sts_success THEN
2784                RAISE gmo_instantiate_err;
2785            END IF;
2786          END IF ;
2787        /*Bug#7493614 moved the workflow event call to the end of the batch
2788             create procedure */
2789       wf_event.RAISE (p_event_name      => gme_common_pvt.G_BATCH_CREATED
2790                      ,p_event_key       => x_batch_header_rec.batch_id);
2791       IF g_debug <= gme_debug.g_log_procedure THEN
2792          gme_debug.put_line ('Exiting api ' || g_pkg_name || '.' || l_api_name);
2793       END IF;
2794    EXCEPTION
2795       WHEN doc_num_is_not_passed THEN
2796          x_return_status := fnd_api.g_ret_sts_error;
2797          gme_common_pvt.log_message ('GME_DOC_NUM_NOT_PASSED');
2798       WHEN gme_duplicate_batch THEN
2799          x_return_status := fnd_api.g_ret_sts_error;
2800          --FPBug#4898641
2801          IF x_batch_header_rec.batch_type = 0 THEN
2802           gme_common_pvt.log_message ('GME_DUP_BATCH');
2803          ELSE
2804           gme_common_pvt.log_message ('GME_DUP_FPO');
2805          END IF;
2806       WHEN steps_creation_failure THEN
2807          NULL;
2808       WHEN error_create_phantom OR invalid_header_values OR invalid_recipe THEN
2809          x_return_status := l_return_status;
2810      --FPBug#4351032
2811       WHEN validation_failure OR expected_error OR scaling_failure OR date_exceed_validity_rule OR batch_header_fetch_failure OR error_count_exceeded OR expected_error OR unexpected_error OR invalid_item_substitute OR material_dtl_fetch_failure THEN
2812          x_return_status := fnd_api.g_ret_sts_error;
2813       WHEN error_cont_period THEN
2814          IF (g_debug = gme_debug.g_log_statement) THEN
2815             gme_debug.put_line ('Contiguity period ... _failed');
2816          END IF;
2817 
2818          x_return_status := l_return_status;
2819       WHEN error_non_contiguious THEN
2820          IF (g_debug = gme_debug.g_log_statement) THEN
2821             gme_debug.put_line ('Contiguity period ... not found');
2822          END IF;
2823 
2824          gme_common_pvt.log_message ('GME_NON_CONTIGUOUS_TIME');
2825          x_return_status := 'C';
2826       WHEN conversion_failure THEN
2827          IF l_item_no IS NULL THEN
2828             OPEN cur_item_no (l_item_id, x_batch_header_rec.organization_id);
2829 
2830             FETCH cur_item_no
2831              INTO l_item_no;
2832 
2833             CLOSE cur_item_no;
2834          END IF;
2835 
2836          x_return_status := fnd_api.g_ret_sts_error;
2837          fnd_message.set_name ('GMI', 'IC_API_UOM_CONVERSION_ERROR');
2838          fnd_message.set_token ('ITEM_NO', l_item_no);
2839          fnd_message.set_token ('FROM_UOM', l_from_uom);
2840          fnd_message.set_token ('TO_UOM', l_to_uom);
2841          fnd_msg_pub.ADD;
2842       WHEN  Fixed_process_loss_failure THEN
2843           IF (g_debug = gme_debug.g_log_statement) THEN
2844             gme_debug.put_line ('Failed to apply FPL');
2845          END IF;
2846       WHEN create_by_product_failure THEN
2847          gme_common_pvt.log_message ('GME_API_CREATE_BY_PROD_FAIL');
2848          x_return_status := fnd_api.g_ret_sts_error;
2849 
2850          IF (g_debug = gme_debug.g_log_statement) THEN
2851             gme_debug.put_line ('GME_API_CREATE_BY_PROD_FAIL');
2852          END IF;
2853       WHEN error_in_integer_scale THEN  -- 10624995
2854          gme_common_pvt.log_message ('GME_INTEGER_MULTIPLE_SCALE_ERR');
2855          x_return_status := FND_API.g_ret_sts_error;
2856 
2857          IF (g_debug = gme_debug.g_log_statement) THEN
2858             gme_debug.put_line ('Integer scaling failed for non scaled batch..  should not happen !!');
2859          END IF;
2860       WHEN inventory_shortage OR create_mo_hdr_err OR create_mo_line_err OR
2861            calc_mtl_req_date_err OR gmo_instantiate_err OR wip_entity_err THEN
2862          x_return_status := l_return_status;
2863       WHEN error_truncate_date THEN
2864          IF (g_debug = gme_debug.g_log_statement) THEN
2865             gme_debug.put_line ('truncate date procedure error');
2866          END IF;
2867 
2868          x_return_status := fnd_api.g_ret_sts_error;
2869       --FPBug#4395561
2870       WHEN create_flex_failure THEN
2871          x_return_status := l_return_status;
2872          IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
2873             gme_debug.put_line ('Creating the default values of the DFF failure');
2874          END IF;
2875      -- Rajesh Patangya Bug # 6752637
2876       WHEN update_step_mtq_failure THEN
2877          x_return_status := fnd_api.g_ret_sts_error;
2878          IF (g_debug = gme_debug.g_log_statement) THEN
2879             gme_debug.put_line ('MTQ Calculation failure');
2880          END IF;
2881       WHEN OTHERS THEN
2882          IF g_debug <= gme_debug.g_log_unexpected THEN
2883             gme_debug.put_line (   'When others exception in '
2884                                 || g_pkg_name
2885                                 || '.'
2886                                 || l_api_name
2887                                 || ' Error is '
2888                                 || SQLERRM);
2889          END IF;
2890 
2891          fnd_msg_pub.add_exc_msg (g_pkg_name, l_api_name);
2892 
2893          IF (g_debug = gme_debug.g_log_statement) THEN
2894             gme_debug.put_line (SQLERRM);
2895          END IF;
2896          x_return_status := fnd_api.g_ret_sts_unexp_error;
2897    END create_batch;
2898 
2899  /************************************************************
2900  *  10-JAN-2008 Rajesh Patangya Bug # 6752637                 *
2901  *   UPDATE_STEP_MTQ                                          *
2902  *   MTQ Quantity should be calculated based on product       *
2903  *************************************************************/
2904 
2905    FUNCTION update_step_mtq (p_batch_id IN NUMBER)
2906                    RETURN BOOLEAN IS
2907 
2908       l_batch_steps         gme_batch_steps%ROWTYPE;
2909       l_calculated_mtq      gme_batch_steps.minimum_transfer_qty%TYPE;
2910       l_api_name            CONSTANT VARCHAR2 (30) := 'UPDATE_STEP_MTQ';
2911 
2912       l_numerator           NUMBER;
2913       l_total_output_qty    NUMBER;
2914       l_step_qty            NUMBER;
2915 
2916      CURSOR step_mtq_cursor (x_batch_id gme_batch_header.batch_id%TYPE) IS
2917        SELECT *
2918        FROM  gme_batch_steps
2919        WHERE batch_id = x_batch_id ;
2920 
2921      CURSOR calculate_mtq_cursor (x_batch_id gme_batch_header.batch_id%TYPE,
2922                          x_routingstep_id fm_rout_dtl.routingstep_id%TYPE) IS
2923 
2924      -- Bug 8226667 - Changed select from inline calculation to using variables.
2925 /*
2926      SELECT
2927         (frh.routing_qty * NVL(frd.minimum_transfer_qty,0)
2928         * DECODE(fmd.detail_uom, iim.primary_uom_code, fmd.qty,
2929           inv_convert.inv_um_convert
2930                   (fmd.inventory_item_id,
2931                    5,
2932                    fmd.qty,
2933                    fmd.detail_uom,
2934                    iim.primary_uom_code,
2935                    NULL,NULL)
2936                 )
2937          )
2938         / (ffm.total_output_qty * frd.step_qty)
2939 */
2940      SELECT
2941         (frh.routing_qty * NVL(frd.minimum_transfer_qty,0)
2942         * DECODE(fmd.detail_uom, iim.primary_uom_code, fmd.qty,
2943           inv_convert.inv_um_convert
2944                   (fmd.inventory_item_id,
2945                    5,
2946                    fmd.qty,
2947                    fmd.detail_uom,
2948                    iim.primary_uom_code,
2949                    NULL,NULL)
2950                 )
2951          ),
2952         ffm.total_output_qty,
2953         frd.step_qty
2954       FROM fm_form_mst ffm,
2955            fm_matl_dtl fmd,
2956            fm_rout_hdr frh,
2957            fm_rout_dtl frd,
2958            mtl_system_items iim,
2959            gme_batch_header gbh,
2960            gmd_recipe_validity_rules ffe
2961       WHERE gbh.batch_id   = x_batch_id
2962         AND ffm.formula_id = gbh.formula_id
2963         AND ffm.formula_id = fmd.formula_id
2964 	AND iim.organization_id = NVL(ffe.organization_id,iim.organization_id)
2965         AND fmd.inventory_item_id = ffe.inventory_item_id
2966         AND iim.inventory_item_id = fmd.inventory_item_id
2967 	AND iim.organization_id = fmd.organization_id
2968         AND frh.routing_id = gbh.routing_id
2969         AND frh.routing_id = frd.routing_id
2970         AND frd.routingstep_id = l_batch_steps.routingstep_id
2971         AND ffe.recipe_validity_rule_id = gbh.recipe_validity_rule_id ;
2972 
2973    BEGIN
2974         OPEN step_mtq_cursor (p_batch_id);
2975         LOOP
2976            FETCH step_mtq_cursor INTO l_batch_steps ;
2977            EXIT WHEN step_mtq_cursor%NOTFOUND;
2978 
2979            IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
2980              gme_debug.put_line (' MTQ = ' || NVL(l_batch_steps.minimum_transfer_qty,0)
2981              || ' Step_qty = ' || NVL(l_batch_steps.plan_step_qty,0)
2982              || ' Routingstep_id = ' || l_batch_steps.routingstep_id );
2983            END IF;
2984 
2985            IF NVL(l_batch_steps.minimum_transfer_qty,0) > 0 AND
2986               NVL(l_batch_steps.plan_step_qty,0) > 0 THEN
2987 
2988               -- Bug 8226667 - Changed select from inline calculation to using variables.
2989               OPEN calculate_mtq_cursor (p_batch_id, l_batch_steps.routingstep_id);
2990               FETCH calculate_mtq_cursor INTO l_numerator, l_total_output_qty, l_step_qty  ;
2991               CLOSE calculate_mtq_cursor ;
2992 
2993               IF (l_step_qty * l_total_output_qty) > 0 THEN
2994                  l_calculated_mtq := l_numerator / (l_step_qty * l_total_output_qty);
2995 
2996                  UPDATE gme_batch_steps
2997                    SET minimum_transfer_qty = l_calculated_mtq
2998                  WHERE batch_id = l_batch_steps.batch_id
2999                    AND routingstep_id =  l_batch_steps.routingstep_id
3000                    AND batchstep_id = l_batch_steps.batchstep_id ;
3001 
3002                  IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
3003                      gme_debug.put_line (' Update Calculated MTQ = ' || l_calculated_mtq );
3004                  END IF;
3005               ELSE
3006                  IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
3007                      gme_debug.put_line (' Cannot Calculated MTQ for step id ' || l_batch_steps.routingstep_id);
3008                      gme_debug.put_line (' step qty is     ' || l_step_qty);
3009                      gme_debug.put_line (' total output is ' || l_total_output_qty);
3010                  END IF;
3011                  NULL;  -- This is here just in case debug is not on.
3012               END IF;
3013            END IF;
3014         END LOOP ;
3015         CLOSE step_mtq_cursor;
3016 
3017       RETURN TRUE ;
3018 
3019    EXCEPTION
3020       WHEN no_data_found THEN
3021          RETURN TRUE ;
3022       WHEN OTHERS THEN
3023          fnd_msg_pub.add_exc_msg (g_pkg_name, l_api_name);
3024          IF (NVL(G_DEBUG,-1) = GME_DEBUG.G_LOG_STATEMENT) THEN
3025             gme_debug.put_line (SQLERRM);
3026          END IF;
3027          RETURN FALSE ;
3028    END update_step_mtq ;
3029 
3030 END gme_create_batch_pvt;