1 package body SSP_PAB_PKG as
2 /*$Header: sppabapi.pkb 120.5 2006/12/09 16:41:34 kthampan noship $
3 +==============================================================================+
4 | Copyright (c) 1994 Oracle Corporation |
5 | Redwood Shores, California, USA |
6 | All rights reserved. |
7 +==============================================================================+
8 --
9 Name
10 Statutory Paternity Pay (Birth) Business Process
11 --
12 Purpose
13 To perform calculation of entitlement and payment for PAB purposes
14 --
15 History
16 17 Oct 02 2690305 A Blinko Created from SSP_SMP_PKG
17 10 Jan 03 A Blinko Amended latest_ppp_start_date
18 27 Jan 03 G Butler nocopy fix - added 2nd dummy variable to
19 average_earnings to act as placeholder
20 for OUT param from ssp_ern_ins
21 01 Feb 03 2774903 A Blinko Fixed check_death procedure
22 11 Feb 03 2772479 A Blinko Late Absence Notification stoppage no
23 no longer created
24 24 Oct 03 3208325 A Blinko Replaced hardcoded SATURDAY and
25 SUNDAY references
26 16 Mar 04 3509432 npershad Modified the call to create_stoppage
27 procedure to rectify misleading stoppage
28 date for 'Some work done' stoppage.
29 29 Mar 04 3516539 skhandwa Added condition in the cursor to fetch
30 termination date for latest assignment
31 07 Jun 04 3598838 A Blinko Now only first absence is recognised
32 12 Jul 04 3682122 A Blinko Changes for recalculating lump sum
33 updates
34 14 Mar 05 4226911 npershad Modified the cursor csr_no_of_absences in
35 procedure generate_payments to get a correct
36 count of absence records.
37 18 Oct 05 4670360 KThampan Amended parameter's order of function
38 LATEST_PPP_START_DATE
39 09 Feb 06 4891953 Kthampan Fixed performance bug.
40 23 Aug 06 5482199 KThampan Change from per_people_f and per_assignments_f
41 to per_all_people_f and per_all_assignments_f
42 19 Spe 06 5547703 KThampan Amend pab_control to call generate_payments
43 with insert-mode if absence is > 0 and
44 also change csr_check_if_existing_entries
45 not to reference from per_absence_attendances
46 table
47 */
48 --------------------------------------------------------------------------------
49 g_package varchar2(33) := ' ssp_pab_pkg.'; -- Global package name
50 --
51 cursor csr_absence_details (p_maternity_id in number) is
52 --
53 -- Get details of the initial paternity leave for a paternity
54 --
55 select absence.absence_attendance_id,
56 absence.date_start,
57 nvl (absence.date_end, hr_general.end_of_time) date_end,
58 absence.date_notification,
59 absence.accept_late_notification_flag
60 from
61 per_absence_attendances ABSENCE
62 where absence.maternity_id = p_maternity_id
63 and absence.absence_attendance_id =
64 (select min(paa_tab.absence_attendance_id)
65 from per_absence_attendances paa_tab
66 where paa_tab.maternity_id = absence.maternity_id);
67 --
68 --------------------------------------------------------------------------------
69 cursor csr_personal_details (p_maternity_id in number) is
70 --
71 -- Get details of the paternal person
72 --
73 select maternity.person_id,
74 maternity.due_date,
75 ssp_pab_pkg.qualifying_week (due_date) QW,
76 ssp_pab_pkg.expected_week_of_confinement (due_date) EWC,
77 maternity.maternity_id,
78 maternity.actual_birth_date,
79 maternity.live_birth_flag,
80 maternity.start_date_with_new_employer,
81 maternity.MPP_start_date APP_start_date,
82 maternity.notification_of_birth_date,
83 maternity.start_date_maternity_allowance,
84 maternity.pay_SMP_as_lump_sum pay_PAB_as_lump_sum,
85 person.date_of_death,
86 service.date_start,
87 nvl (service.final_process_date, hr_general.end_of_time) FINAL_PROCESS_DATE
88 from ssp_maternities MATERNITY,
89 per_all_people_f PERSON,
90 per_periods_of_service SERVICE
91 where person.person_id = maternity.person_id
92 and person.person_id = service.person_id
93 and maternity.maternity_id = p_maternity_id
94 and service.date_start between person.effective_start_date
95 and person.effective_end_date
96 and service.date_start = (select max(serv.date_start)
97 from per_periods_of_service serv
98 where serv.person_id = person.person_id);
99 --------------------------------------------------------------------------------
100 person csr_personal_details%rowtype;
101 g_PAB_element csr_PAB_element_details%rowtype;
102 g_PAB_Correction_element csr_PAB_element_details%rowtype;
103 --------------------------------------------------------------------------------
104 l_sunday varchar2(100) := to_char(to_date('07/01/2001','DD/MM/YYYY'),'DAY');
105
106 function QUALIFYING_WEEK (p_due_date in date) return date is
107 --
108 -- Returns the date on which the QW starts
109 --
110 -- QW is the EWC minus the QW weeks from the PAB element
111 --
112 l_QW date;
113 l_PAB_element csr_PAB_element_details%rowtype;
114 --
115 begin
116 --
117 open csr_PAB_element_details (p_due_date,c_PAB_element_name);
118 fetch csr_PAB_element_details into l_PAB_element;
119 close csr_PAB_element_details;
120 --
121 l_QW := expected_week_of_confinement(p_due_date)
122 - l_PAB_element.qualifying_week;
123 --
124 return l_QW;
125 --
126 end QUALIFYING_WEEK;
127 --------------------------------------------------------------------------------
128 Function CONTINUOUS_EMPLOYMENT_DATE (p_due_date in date)
129 return date is
130 --
131 -- The continuous employment start date is the date on which the person must
132 -- have been employed (and continuously from then to the MW) in order to
133 -- qualify for SAP. It is the MW minus the continuous employment period
134 -- specified on the SAP element.
135 -- A woman must have started work on or before the last day of the
136 -- week which starts 182 days (26 weeks) before the last day of the MW. In
137 -- SAP weeks start on Sunday and end on Saturday.
138 --
139 l_PAB_element csr_PAB_element_details%rowtype;
140 l_Continuously_employed_since date;
141 l_saturday varchar2(100) := to_char(to_date('06/01/2001','DD/MM/YYYY'),'DAY');
142 --
143 begin
144 --
145 open csr_PAB_element_details (p_due_date,c_PAB_element_name);
146 fetch csr_PAB_element_details into l_PAB_element;
147 close csr_PAB_element_details;
148 --
149 l_Continuously_employed_since :=
150 next_day(next_day(
151 QUALIFYING_WEEK(p_due_date) ,l_saturday)
152 - (l_PAB_element.continuous_employment_period),l_saturday);
153 --
154 return l_Continuously_employed_since;
155 --
156 end continuous_employment_date;
157 --------------------------------------------------------------------------------
158 procedure get_PAB_correction_element (p_effective_date in date) is
159 --
160 l_proc varchar2(72) := g_package||'get_PAB_correction_element';
161 --
162 procedure check_parameters is
163 begin
164 --
165 hr_utility.trace (l_proc||' p_effective_date = '
166 ||to_char (p_effective_date));
167 --
168 hr_api.mandatory_arg_error (
169 p_api_name => l_proc,
170 p_argument => 'effective_date',
171 p_argument_value=> p_effective_date);
172 end check_parameters;
173 --
174 begin
175 --
176 hr_utility.set_location (l_proc,1);
177 --
178 check_parameters;
179 --
180 open csr_PAB_element_details (p_effective_date,c_PAB_corr_element_name);
181 fetch csr_PAB_element_details into g_PAB_Correction_element;
182 close csr_PAB_element_details;
183 --
184 hr_utility.set_location (l_proc,100);
185 --
186 end get_PAB_correction_element;
187 --------------------------------------------------------------------------------
188 procedure get_PAB_element (p_effective_date in date) is
189 --
190 l_proc varchar2(72) := g_package||'get_PAB_element';
191 --
192 procedure check_parameters is
193 begin
194 --
195 hr_utility.trace (l_proc||' p_effective_date = '
196 ||to_char (p_effective_date));
197 --
198 hr_api.mandatory_arg_error (
199 p_api_name => l_proc,
200 p_argument => 'effective_date',
201 p_argument_value=> p_effective_date);
202 end check_parameters;
203 --
204 begin
205 --
206 hr_utility.set_location (l_proc,1);
207 --
208 check_parameters;
209 --
210 open csr_PAB_element_details (p_effective_date,c_PAB_element_name);
211 fetch csr_PAB_element_details into g_PAB_element;
212 close csr_PAB_element_details;
213 --
214 hr_utility.set_location (l_proc,100);
215 --
216 end get_PAB_element;
217 --------------------------------------------------------------------------------
218 function EARLIEST_PPP_START_DATE (p_birth_date in date) return date is
219 --
220 -- The earliest PPP start date, under normal circumstances is the
221 -- child expected date minus
222 -- the number of weeks specified on the SAP element for earliest SAP start
223 --
224 l_earliest_PPP_start date;
225 l_PAB_element csr_PAB_element_details%rowtype;
226 --
227 begin
228 --
229 open csr_PAB_element_details (p_birth_date,c_PAB_element_name);
230 fetch csr_PAB_element_details into l_PAB_element;
231 close csr_PAB_element_details;
232 --
233 l_earliest_PPP_start := p_birth_date
234 - (l_PAB_element.earliest_start_of_PPP);
235 --
236 return l_earliest_PPP_start;
237 --
238 end earliest_PPP_start_date;
239 --------------------------------------------------------------------------------
240 function LATEST_PPP_START_DATE (p_birth_date in date,
241 p_ewc in date,
242 p_due_date in date) return date is
243 --
244 l_latest_PPP_start date;
245 l_PAB_element csr_PAB_element_details%rowtype;
246 --
247 begin
248 --
249 open csr_PAB_element_details (p_birth_date,c_PAB_element_name);
250 fetch csr_PAB_element_details into l_PAB_element;
251 close csr_PAB_element_details;
252 --
253 if p_birth_date < p_due_date then
254 l_latest_PPP_start := greatest(p_birth_date,p_ewc)
255 + (l_PAB_element.latest_end_of_PPP - 7);
256 else
257 l_latest_PPP_start := p_birth_date + (l_PAB_element.latest_end_of_PPP - 7);
258 end if;
259 --
260 return l_latest_PPP_start;
261 --
262 end latest_ppp_start_date;
263 --------------------------------------------------------------------------------
264 function expected_week_of_confinement (p_due_date in date) return date is
265 --
266 l_ewc date;
267 --
268 begin
269 --
270 l_ewc := (next_day(p_due_date,l_sunday)-7);
271 --
272 return l_ewc;
273 --
274 end expected_week_of_confinement;
275 --------------------------------------------------------------------------------
276 function MATERNITY_RECORD_EXISTS (p_person_id in number) return boolean is
277 --
278 cursor maternity_record is
279 select 1
280 from ssp_maternities
281 where person_id = p_person_id;
282 --
283 l_dummy number (1);
284 l_maternity_record_exists boolean;
285 --
286 begin
287 --
288 open maternity_record;
289 fetch maternity_record into l_dummy;
290 l_maternity_record_exists := maternity_record%found;
291 close maternity_record;
292 --
293 return l_maternity_record_exists;
294 --
295 end maternity_record_exists;
296 --------------------------------------------------------------------------------
297 function AVERAGE_EARNINGS return number is
298 --
299 l_average_earnings number := null;
300 l_effective_date date := null;
301 l_dummy number;
302 l_dummy2 number; -- nocopy fix, placeholder variable
303 l_user_entered varchar2(30) := 'N'; --DFoster 1304683
304 l_absence_category varchar2(30) := 'GB_PAT_BIRTH'; --DFoster 1304683
305 l_payment_periods number := null; --DFoster 1304683
306 l_proc varchar2(72) := g_package||'average_earnings';
307 --
308 cursor csr_average_earnings is
309 select average_earnings_amount
310 from ssp_earnings_calculations
311 where person_id = person.person_id
312 and effective_date = l_effective_date;
313 --
314 begin
315 --
316 hr_utility.set_location ('Entering '||l_proc,1);
317 --
318 l_effective_date := greatest(person.QW, person.date_start);
319 --
320 open csr_average_earnings;
321 fetch csr_average_earnings into l_average_earnings;
322 --
323 if csr_average_earnings%notfound
324 then
325 ssp_ern_ins.ins (p_earnings_calculations_id => l_dummy,
326 p_object_version_number => l_dummy2,
327 p_person_id => person.person_id,
328 p_effective_date => l_effective_date,
329 p_average_earnings_amount => l_average_earnings,
330 p_user_entered => l_user_entered, --DFoster 1304683
331 p_absence_category => l_absence_category, --DFoster 1304683
332 p_payment_periods => l_payment_periods); --DFoster 1304683
333 end if;
334 --
335 close csr_average_earnings;
336 --
337 hr_utility.set_location ('Leaving '||l_proc,10);
338 --
339 return l_average_earnings;
340 --
341 end average_earnings;
342 --------------------------------------------------------------------------------
343 function entitled_to_PAB (p_maternity_id in number) return boolean is
344 --
345 -- See header for description of this procedure.
346 --
347 no_prima_facia_entitlement exception;
348 invalid_absence_date exception;
349 l_work_start_date date := hr_general.end_of_time;
350 stoppage_end_date date := null;
351 no_of_absence_periods integer := 0;
352 l_proc varchar2(72) := g_package||'entitled_to_PAB';
353 l_keep_stoppages boolean default FALSE;
354 --
355 cursor csr_no_of_absences is
356 --
357 select count (*)
358 from per_absence_attendances
359 where person_id = person.person_id
360 and maternity_id = p_maternity_id
361 and absence_attendance_id =
362 (select min(paa_tab.absence_attendance_id)
363 from per_absence_attendances paa_tab
364 where paa_tab.maternity_id = p_maternity_id);
365 --
366 -- returns entries associated with a maternity_id.
367 cursor csr_check_if_existing_entries is
368 --
369 select /*+ ORDERED use_nl(paa,paaf,etype,entry) */
370 entry.element_entry_id,
371 entry.effective_start_date
372 from per_all_assignments_f PAAF,
373 pay_element_types_f ETYPE,
374 pay_element_entries_f ENTRY
375 where PAAF.person_id = person.person_id
376 and ETYPE.element_name = c_PAB_element_name
377 and ETYPE.legislation_code = 'GB'
378 and ENTRY.element_type_id = ETYPE.element_type_id
379 and ENTRY.creator_type = c_PAB_creator_type
380 and ENTRY.creator_id = p_maternity_id
381 and ENTRY.assignment_id = PAAF.assignment_id
382 and not exists (
383 --
384 -- Do not select entries which have already had reversal action
385 -- taken against them because they are effectively cancelled out.
386 --
387 select 1
388 from pay_element_entries_f ENTRY2
389 where entry.element_entry_id= entry2.target_entry_id
390 and entry.assignment_id = entry2.assignment_id)
391 --
392 and not exists (
393 --
394 -- Do not select reversal entries
395 --
396 select 1
397 from pay_element_links_f LINK,
398 pay_element_types_f TYPE
399 where link.element_link_id = entry.element_link_id
400 and entry.effective_start_date between link.effective_start_date and link.effective_end_date
401 and link.element_type_id = type.element_type_id
402 and link.effective_start_date between type.effective_start_date and type.effective_end_date
403 and type.element_name = c_PAB_corr_element_name);
404 --
405 l_existing_entries csr_check_if_existing_entries%rowtype;
406 --
407 procedure create_stoppage (
408 --
409 -- Create a stoppage of payment for PAB
410 --
411 p_reason in varchar2,
412 p_withhold_from in date,
413 p_withhold_to in date default null) is
414 --
415 l_proc varchar2(72) := g_package||'create_stoppage';
416 l_dummy number;
417 l_reason_id number;
418 --
419 procedure check_parameters is
420 --
421 begin
422 --
423 hr_utility.trace (l_proc||' p_reason = '||p_reason);
424 hr_utility.trace (l_proc||' withhold from '||to_char (p_withhold_from));
425 hr_utility.trace (l_proc||' withhold to '||to_char (p_withhold_to));
426 --
427 hr_api.mandatory_arg_error (
428 p_api_name => l_proc,
429 p_argument => 'reason',
430 p_argument_value=> p_reason);
431 --
432 hr_api.mandatory_arg_error (
433 p_api_name => l_proc,
434 p_argument => 'withhold_from',
435 p_argument_value=> p_withhold_from);
436 --
437 end check_parameters;
438 --
439 begin
440 --
441 hr_utility.set_location (l_proc,1);
442 --
443 check_parameters;
444 --
445 l_reason_id := ssp_smp_support_pkg.withholding_reason_id (
446 g_PAB_element.element_type_id,
447 p_reason);
448 --
449 if not ssp_smp_support_pkg.stoppage_overridden (
450 p_maternity_id => p_maternity_id,
451 p_reason_id => l_reason_id)
452 then
453 --
454 -- Only create the stoppage if there is not already a stoppage marked
455 -- as over--ridden. Thus, overriding a stoppage effectively blocks that
456 -- reason being used to withhold payment for this person.
457 --
458 ssp_stp_ins.ins (p_withhold_from => p_withhold_from,
459 p_withhold_to => p_withhold_to,
460 p_stoppage_id => l_dummy,
461 p_object_version_number => l_dummy,
462 p_maternity_id => p_maternity_id,
463 p_user_entered => 'N',
464 p_reason_id => l_reason_id);
465 else
466 hr_utility.trace (l_proc||' Stoppage is overridden');
467 end if;
468 --
469 hr_utility.set_location (l_proc,100);
470 --
471 end create_stoppage;
472 --
473 procedure remove_stoppages is
474 --
475 -- Remove old system, non-overridden stoppages
476 --
477 cursor csr_stoppages is
478 select stoppage_id
479 from ssp_stoppages
480 where user_entered <>'Y'
481 and override_stoppage <> 'Y'
482 and maternity_id = p_maternity_id;
483 --
484 l_dummy number;
485 l_proc varchar2 (72) := g_package||'remove_stoppages';
486 --
487 begin
488 --
489 hr_utility.set_location (l_proc,1);
490 --
491 for each_stoppage in csr_stoppages LOOP
492 ssp_stp_del.del (p_stoppage_id => each_stoppage.stoppage_id,
493 p_object_version_number => l_dummy);
494 end loop;
495 --
496 hr_utility.set_location (l_proc,100);
497 --
498 end remove_stoppages;
499 --
500 procedure check_employment_end is
501
502 cursor csr_termination_date is
503 select actual_termination_date
504 from per_periods_of_service
505 where person_id = person.person_id
506 -- 3516539 Added condition to obtain termination date for latest assignment
507 and period_of_service_id = (select max(period_of_service_id)
508 from per_periods_of_service ppos
509 where ppos.person_id = person.person_id);
510 --
511 l_termination_date date := null;
512 l_proc varchar2(72) := g_package||'check_employment_end';
513 --
514 begin
515 --
516 hr_utility.set_location (l_proc,1);
517 --
518 open csr_termination_date;
519 fetch csr_termination_date into l_termination_date;
520 close csr_termination_date;
521 --
522 if l_termination_date < person.actual_birth_date then
523 --
524 -- Stop all PAB payment for the Birth because the person left
525 -- before the PPP start date.
526 --
527 create_stoppage (p_withhold_from => person.actual_birth_date,
528 p_reason => 'Not employed on Birth Date');
529 end if;
530 --
531 hr_utility.set_location (l_proc,100);
532 --
533 end check_employment_end;
534 --
535 procedure check_continuity_rule is
536 --
537 -- Check that the person has the right amount of continuous service to
538 -- qualify for SAP
539 --
540 cursor period_of_service is
541 --
542 -- Check the period of service length up to the MW start date
543 --
544 select 1
545 from per_periods_of_service
546 where person_id = person.person_id
547 and date_start <= ssp_pab_pkg.continuous_employment_date(person.due_date)
548 and nvl (actual_termination_date, hr_general.end_of_time) >= person.QW;
549 --
550 l_dummy number (1);
551 l_proc varchar2 (72) := g_package||'check_continuity_rule';
552 --
553 begin
554 --
555 hr_utility.set_location (l_proc,1);
556 --
557 open period_of_service;
558 fetch period_of_service into l_dummy;
559 --
560 if period_of_service%notfound then
561 --
562 -- Stop all SAP payment for the Adoption because the person has not
563 -- been continuously employed for long enough.
564 --
565 create_stoppage (p_withhold_from => person.APP_start_date,
566 p_reason => 'Insufficient employment');
567 end if;
568 --
569 close period_of_service;
570 --
571 hr_utility.set_location (l_proc,100);
572 --
573 end check_continuity_rule;
574 --
575 procedure check_start_date is
576
577 l_proc varchar2 (72) := g_package||'check_start_date';
578 --
579 l_latest_PPP_start date;
580 l_PAB_element csr_PAB_element_details%rowtype;
581 --
582 begin
583 --
584 hr_utility.set_location (l_proc,1);
585 --
586 open csr_PAB_element_details (person.actual_birth_date,c_PAB_element_name);
587 fetch csr_PAB_element_details into l_PAB_element;
588 close csr_PAB_element_details;
589 --
590 if person.app_start_date > greatest(person.ewc,person.actual_birth_date)
591 + (l_PAB_element.latest_end_of_PPP - 14)
592 then
593
594 create_stoppage (p_withhold_from => person.APP_start_date + 7,
595 p_reason => 'Max PPP Period Exceeded');
596
597 end if;
598 --
599 hr_utility.set_location (l_proc,100);
600 --
601 end check_start_date;
602
603 procedure check_stillbirth is
604 --
605 -- Check the pregnancy condition for qualification for PAB
606 --
607 l_proc varchar2 (72) := g_package||'check_stillbirth';
608 --
609 begin
610 --
611 hr_utility.set_location (l_proc,1);
612 --
613 -- Woman must be still pregnant, have had a live birth, or have had a
614 -- stillbirth after the threshhold week to be eligible for PAB
615 --
616 if NOT (person.actual_birth_date is null
617 or person.live_birth_flag = 'Y'
618 or person.actual_birth_date > person.EWC
619 - g_PAB_element.stillbirth_threshold_week)
620 then
621 --
622 -- Stop SMP payment from the start of the week in which the absence
623 -- started.
624 --
625 create_stoppage (p_withhold_from => person.APP_start_date,
626 p_reason => 'Stillbirth');
627 end if;
628 --
629 hr_utility.set_location (l_proc,100);
630 --
631 end check_stillbirth;
632 --
633 procedure check_new_employer is
634 --
635 -- Check the person has not been employed by a new employer after the
636 -- child placement
637 --
638 l_proc varchar2 (72) := g_package||'check_new_employer';
639 --
640 begin
641 --
642 hr_utility.set_location (l_proc,1);
643 --
644 if person.start_date_with_new_employer >= person.actual_birth_date then
645 --
646 -- Stop SAP payment from the start of the week in which the person
647 -- started work for a new employer after the placement of her child.
648 --
649 create_stoppage (p_withhold_from => ssp_smp_support_pkg.start_of_week
650 (person.start_date_with_new_employer),
651 p_reason => 'Worked for another employer');
652 end if;
653 --
654 hr_utility.set_location (l_proc,100);
655 --
656 end check_new_employer;
657 --
658 procedure check_maternity_allowance is
659 --
660 -- SAP ceases when SMA starts.
661 --
662 l_proc varchar2 (72) := g_package||'check_maternity_allowance';
663 --
664 begin
665 --
666 hr_utility.set_location (l_proc,1);
667 --
668 if person.start_date_maternity_allowance is not null then
669 --
670 -- Stop SAP payment from the start of the week in which SMA was first
671 -- paid.
672 --
673 create_stoppage (p_withhold_from => ssp_smp_support_pkg.start_of_week
674 (person.start_date_maternity_allowance),
675 p_reason => 'Employee is receiving SMA');
676 end if;
677 --
678 hr_utility.set_location (l_proc,100);
679 --
680 end check_maternity_allowance;
681 --
682 procedure check_death is
683 --
684 -- PAB ceases after the death of the person.
685 --
686 l_proc varchar2 (72) := g_package||'check_death';
687 --
688 cursor csr_check_death is
689 select ppf.date_of_death
690 from per_all_people_f ppf
691 where ppf.person_id = person.person_id
692 and ppf.date_of_death is not null;
693 --
694 l_death_date date;
695 --
696 begin
697 --
698 hr_utility.set_location (l_proc,1);
699 --
700 -- PAB ceases on the Saturday following death
701 --
702 l_death_date := null;
703 --
704 open csr_check_death;
705 fetch csr_check_death into l_death_date;
706 close csr_check_death;
707 --
708 if l_death_date is not null then
709 create_stoppage (p_withhold_from => next_day (l_death_date,
710 l_sunday),
711 p_reason => 'Employee died');
712 end if;
713 --
714 hr_utility.set_location (l_proc,100);
715 --
716 end check_death;
717 --
718 procedure check_average_earnings is
719 --
720 -- The person must earn enough to qualify for SAP
721 --
722 l_proc varchar2 (72) := g_package||'check_average_earnings';
723 l_average_earnings number := average_earnings;
724 l_reason_for_no_earnings varchar2 (80) := null;
725 earnings_not_derived exception;
726 --
727 begin
728 --
729 hr_utility.set_location (l_proc,1);
730 --
731 if l_average_earnings = 0
732 then
733 --
734 -- If the average earnings figure returned is zero then check that
735 -- no error message was set. Error messages will be set for system-
736 -- generated average earnings when the earnings could not be derived
737 -- for some reason, but to allow this procedure to continue, no error
738 -- will be raised.
739 --
740 l_reason_for_no_earnings:=ssp_smp_support_pkg.average_earnings_error;
741 --
742 if l_reason_for_no_earnings is not null then
743 create_stoppage (p_withhold_from => person.aPP_start_date,
744 p_reason => l_reason_for_no_earnings);
745 --
746 raise earnings_not_derived;
747 end if;
748 end if;
749 --
750 if l_average_earnings
751 < ssp_smp_support_pkg.NI_Lower_Earnings_Limit (person.QW)
752 then
753 --
754 -- Stop SAP payment from the APP start date
755 --
756 create_stoppage (p_withhold_from => person.APP_start_date,
757 p_reason => 'Earnings too low');
758 end if;
759 --
760 hr_utility.set_location (l_proc,100);
761 --
762 exception
763 --
764 when earnings_not_derived then
765 --
766 -- Exit silently from this procedure
767 --
768 hr_utility.trace (l_proc||' Earnings not derived');
769 null;
770 --
771 end check_average_earnings;
772 --
773 procedure check_birth_confirmation is
774 --
775 -- Check that confirmation of birth was received in good time.
776 --
777 l_proc varchar2 (72) := g_package||'check_birth_confirmation';
778 --
779 begin
780 --
781 hr_utility.set_location (l_proc,1);
782 --
783 hr_utility.set_location (l_proc,100);
784 --
785 end check_birth_confirmation;
786 --
787 procedure check_parameters is
788 --
789 begin
790 --
791 hr_utility.trace (l_proc||' p_maternity_id = '
792 ||to_char (p_maternity_id));
793 --
794 hr_api.mandatory_arg_error (
795 p_api_name => l_proc,
796 p_argument => 'maternity_id',
797 p_argument_value=> p_maternity_id);
798 --
799 end check_parameters;
800 --
801 begin
802 --
803 hr_utility.set_location (l_proc,1);
804 --
805 check_parameters;
806 --
807 -- Get the details of the woman and her maternity.
808 --
809 open csr_personal_details (p_maternity_id);
810 fetch csr_personal_details into person;
811 --
812 if csr_personal_details%notfound
813 then
814 --
815 -- If no maternity record exists then there can be no entitlement to SAP
816 --
817 close csr_personal_details;
818 --
819 hr_utility.trace (l_proc||' Person has no maternity record - exiting');
820 --
821 raise no_prima_facia_entitlement;
822 end if;
823 --
824 close csr_personal_details;
825 --
826 if person.APP_start_date is null then
827 --
828 -- If the APP has not started then there is no entitlement to SAP.
829 --
830 hr_utility.trace (l_proc||' Person has no APP start date - exiting');
831 --
832 raise no_prima_facia_entitlement;
833 end if;
834 --
835 -- Count how many absences there are for the maternity.
836 --
837 open csr_no_of_absences;
838 fetch csr_no_of_absences into no_of_absence_periods;
839 close csr_no_of_absences;
840 --
841 if no_of_absence_periods = 0
842 then
843 --
844 -- check if entries exist despite there being no absence
845 --
846 open csr_check_if_existing_entries;
847 fetch csr_check_if_existing_entries into l_existing_entries;
848 --
849 if csr_check_if_existing_entries%NOTFOUND
850 then
851 hr_utility.trace (l_proc||' Person has not stopped work - exiting');
852 raise no_prima_facia_entitlement;
853 end if;
854 --
855 -- if entries are found then the absence has been deleted and entries remain
856 -- that must be dealt with
857 --
858 while csr_check_if_existing_entries%FOUND LOOP
859 fetch csr_check_if_existing_entries into l_existing_entries;
860 end loop;
861 --
862 close csr_check_if_existing_entries;
863 l_keep_stoppages := TRUE;
864 end if;
865 --
866 -- Having established a prima facia entitlement to SAP, perform checks which
867 -- may lead to creation of stoppages for particular periods.
868 --
869 hr_utility.set_location ('ssp_smp_pkg.entitled_to_PAB',2);
870 --
871 -- Get the SAP legislative parameters.
872 --
873 get_PAB_element (person.due_date);
874 --
875 -- Clear stoppages created by previous calculations of SAP but if an absence
876 -- is being deleted, then must keep stoppages so that when later comparison of
877 -- old_entry and hypothetical_entry is done then stoppages are still there.
878 --
879 if not l_keep_stoppages then
880 remove_stoppages;
881 end if;
882 --
883 for absence in csr_absence_details (p_maternity_id) LOOP
884 --
885 -- Check that sufficient notification of absence was given
886 --
887 -- if notification of absence was later than the allowed date
888 -- and there was no acceptable reason for the delay
889 -- or notification of absence was later than the extended allowable date
890 --
891 if (absence.date_notification > absence.date_start
892 - g_PAB_element.MPP_notice_requirement
893 and absence.accept_late_notification_flag = 'N')
894 or (absence.date_notification > person.actual_birth_date
895 + g_PAB_element.MPP_notice_requirement)
896 then
897 --
898 -- Stop SAP payment from the start of the week in which the absence
899 -- starts, to the end of the notice period
900 --
901 stoppage_end_date := g_PAB_element.MPP_notice_requirement
902 + absence.date_start - 1;
903 --
904 /* Bug 2772479 - Stoppage no longer required but may be reintroduced
905
906 create_stoppage (
907 p_withhold_from => ssp_smp_support_pkg.start_of_week
908 (absence.date_start),
909 p_withhold_to => ssp_smp_support_pkg.end_of_week (stoppage_end_date),
910 p_reason => 'Late absence notification');
911 */
912 end if;
913 --
914 hr_utility.set_location ('ssp_sap_pkg.entitled_to_SaP',3);
915 --
916 -- Check for any work done during the APP.
917 --
918 -- Check if this is the first absence period in the APP
919 -- and the absence starts after the APP start date
920 if csr_absence_details%rowcount = 1
921 and absence.date_start > person.APP_start_date
922 then
923 create_stoppage (p_reason => 'Some work was done',
924 p_withhold_from => person.APP_start_date,
925 p_withhold_to => ssp_smp_support_pkg.end_of_week
926 (absence.date_start -1));
927 end if;
928 --
929 -- If this is the last absence period in the MPP
930 -- and the absence period ends before the end of the MPP
931 --
932 if csr_absence_details%rowcount = no_of_absence_periods
933 and absence.date_end < (g_PAB_element.maximum_PPP_weeks * 7)
934 + person.APP_start_date
935 then
936
937
938 --Commented code for Bug Fix 3509432
939 /* create_stoppage (p_reason => 'Some work was done',
940 p_withhold_from => ssp_smp_support_pkg.start_of_week
941 (absence.date_end+1));*/
942
943 --Bug 3509432 start
944 --Only one week is paid, if absence is for > 1 week but < 2 weeks
945 if (absence.date_end - absence.date_start) + 1 > 7 and (absence.date_end - absence.date_start) + 1 < 14 then
946
947 create_stoppage (p_reason => 'Some work was done',
948 p_withhold_from => person.APP_start_date + 7);
949
950 --no weeks are paid,if absence < 1 week
951 elsif (absence.date_end - absence.date_start) + 1 < 7 then
952
953 create_stoppage (p_reason => 'Some work was done',
954 p_withhold_from => person.APP_start_date);
955
956 elsif (absence.date_end - absence.date_start) + 1 = 7 then
957
958 create_stoppage (p_reason => 'Some work was done',
959 p_withhold_from => person.APP_start_date + 7);
960
961 --no stoppage created if absence is equal to 2 weeks
962 elsif absence.date_start is not null and absence.date_end is not null then
963 if (absence.date_end - absence.date_start) + 1 = 14 then
964 null;
965 end if;
966 end if;
967
968 --Bug 3509432 End
969 elsif
970 -- there is a period of work between two absences
971 l_work_start_date < absence.date_start
972 and l_work_start_date < (g_PAB_element.maximum_PPP_weeks * 7)
973 + person.APP_start_date
974 then
975 create_stoppage (p_reason => 'Some work was done',
976 p_withhold_from => ssp_smp_support_pkg.start_of_week
977 (l_work_start_date),
978 p_withhold_to => ssp_smp_support_pkg.end_of_week
979 (absence.date_start -1));
980 --
981 if absence.date_end <> hr_general.end_of_time
982 then
983 l_work_start_date := absence.date_end + 1;
984 else
985 --
986 -- This is not the last absence in the maternity but it has no end date.
987 --
988 hr_utility.trace (l_proc||' ERROR: Invalid null absence end date');
989 --
990 raise invalid_absence_date;
991 end if;
992 end if;
993 end loop;
994 --
995 check_continuity_rule;
996 check_start_date;
997 check_employment_end;
998 check_stillbirth;
999 check_new_employer;
1000 check_maternity_allowance;
1001 check_death;
1002 check_birth_confirmation;
1003 check_average_earnings;
1004 --
1005 -- If we get this far the person is entitled to SAP (though stoppages may apply)
1006 --
1007 return TRUE;
1008 --
1009 exception
1010 --
1011 when invalid_absence_date then
1012 fnd_message.set_name ('PAY', 'HR_6153_ALL_PROCEDURE_FAIL');
1013 fnd_message.set_token ('PROCEDURE','ssp_smp_pkg.entitled_to_PAB');
1014 fnd_message.set_token ('STEP','3');
1015 --
1016 when no_prima_facia_entitlement then
1017 --
1018 -- Exit silently; this will allow us to call this procedure with impunity
1019 -- from absences which are not maternity absences (e.g. via a row trigger)
1020 --
1021 return FALSE;
1022 --
1023 end entitled_to_PAB;
1024 --------------------------------------------------------------------------------
1025 procedure generate_payments(p_maternity_id in number,
1026 p_deleting in boolean default FALSE) is
1027 --
1028 type date_table is table of date index by binary_integer;
1029 type number_table is table of number index by binary_integer;
1030 type varchar_table is table of varchar2 (80) index by binary_integer;
1031 l_proc varchar2(72) := g_package||'generate_payments';
1032 --
1033 type PAB_entry is record (
1034 --
1035 element_entry_id number_table,
1036 element_link_id number_table,
1037 assignment_id number_table,
1038 effective_start_date date_table,
1039 effective_end_date date_table,
1040 amount number_table,
1041 rate varchar_table,
1042 week_commencing date_table,
1043 recoverable_amount number_table,
1044 stopped varchar_table,
1045 dealt_with varchar_table);
1046 --
1047 --
1048 -- A store for all the SAP entries that potentially may be
1049 -- granted to the person.
1050 --
1051 hypothetical_entry PAB_entry;
1052 --
1053 -- A tally of the number of weeks of the APP which are subject to stoppages.
1054 --
1055 l_stopped_weeks number := 0;
1056 --
1057 l_high_rate varchar2 (80) := null;
1058 l_low_rate varchar2 (80) := null;
1059 -- RT entries prob
1060 l_no_of_absence_periods integer := 0;
1061 --
1062 -- p_deleting passed into save_hypothetical_entries, so that logic can be
1063 -- dealt with for deleted absences.
1064 --
1065 procedure save_hypothetical_entries (p_deleting in boolean default false) is
1066 --
1067 -- Having generated the potential SAP entries, reconcile them with any
1068 -- previously granted entries for the same maternity.
1069 --
1070 cursor csr_existing_entries is
1071 --
1072 -- Get all entries and entry values for the Adoption
1073 --
1074 -- Decode the rate code to give the meaning using local variables
1075 -- populated earlier by Calculate_correct_SAP_rate
1076 -- these can then be passed directly into the hr_entry_api's and
1077 -- simplifies comparison with hypo entries
1078 --
1079 select entry.element_entry_id,
1080 entry.element_link_id,
1081 entry.assignment_id,
1082 entry.effective_start_date,
1083 entry.effective_end_date,
1084 -- if in future we get two different rates then a decode can be added here
1085 l_high_rate RATE,
1086 to_date (ssp_smp_support_pkg.value
1087 (entry.element_entry_id,
1088 ssp_sap_pkg.c_week_commencing_name),
1089 'DD-MON-YYYY') WEEK_COMMENCING,
1090 to_number(ssp_smp_support_pkg.value (entry.element_entry_id,
1091 ssp_sap_pkg.c_amount_name)) AMOUNT,
1092 to_number(ssp_smp_support_pkg.value (entry.element_entry_id,
1093 ssp_sap_pkg.c_recoverable_amount_name)) RECOVERABLE_AMOUNT
1094 from pay_element_entries_f ENTRY,
1095 per_all_assignments_f asg
1096 where creator_type = c_PAB_creator_type
1097 and creator_id = p_maternity_id
1098 and asg.person_id = person.person_id
1099 and asg.assignment_id = entry.assignment_id
1100 and entry.effective_start_date between asg.effective_start_date
1101 and asg.effective_end_date
1102 and not exists (
1103 --
1104 -- Do not select entries which have already had reversal action taken
1105 -- against them because they are effectively cancelled out.
1106 --
1107 select 1
1108 from pay_element_entries_f ENTRY2
1109 where entry.element_entry_id= entry2.target_entry_id
1110 and entry.assignment_id = entry2.assignment_id)
1111 --
1112 and not exists (
1113 --
1114 -- Do not select reversal entries
1115 --
1116 select 1
1117 from pay_element_links_f LINK,
1118 pay_element_types_f TYPE
1119 where link.element_link_id = entry.element_link_id
1120 and entry.effective_start_date between link.effective_start_date
1121 and link.effective_end_date
1122 and link.element_type_id = type.element_type_id
1123 and link.effective_start_date between type.effective_start_date
1124 and type.effective_end_date
1125 and type.element_name = c_PAB_corr_element_name);
1126 --
1127 cursor csr_no_of_absences is
1128 --
1129 select count (*)
1130 from per_absence_attendances
1131 where person_id = person.person_id
1132 and maternity_id = p_maternity_id
1133 and absence_attendance_id =
1134 (select min(paa_tab.absence_attendance_id)
1135 from per_absence_attendances paa_tab
1136 where paa_tab.maternity_id = p_maternity_id); --Bug fix 4226911
1137
1138
1139 --
1140 l_ins_corr_ele boolean;
1141 l_dummy number;
1142 Entry_number integer;
1143 l_ern_calc_id number;
1144 l_ob_v_no number;
1145 l_new_ob_v_no number;
1146 l_proc varchar2 (72) := g_package||'save_hypothetical_entries';
1147 --
1148
1149
1150 -- This procedure was a private procedure in the function entitled_to_sap. I
1151 -- wanted to call it within this procedure (generate_payments) aswell, so
1152 -- instead of making it a public procedure I have copied the procedure to here.
1153 --
1154 procedure remove_stoppages is
1155 --
1156 -- Remove old system, non-overridden stoppages
1157 --
1158 cursor csr_stoppages is
1159 select stoppage_id
1160 from ssp_stoppages
1161 where user_entered <>'Y'
1162 and override_stoppage <> 'Y'
1163 and maternity_id = p_maternity_id;
1164 --
1165 l_dummy number;
1166 l_proc varchar2 (72) := g_package||'.remove_stoppages';
1167 --
1168 begin
1169 --
1170 hr_utility.set_location (l_proc,1);
1171 --
1172 for each_stoppage in csr_stoppages LOOP
1173 ssp_stp_del.del (p_stoppage_id => each_stoppage.stoppage_id,
1174 p_object_version_number => l_dummy);
1175
1176 end loop;
1177 --
1178 hr_utility.set_location (l_proc,100);
1179 --
1180 end remove_stoppages;
1181 --
1182 begin
1183 --
1184 hr_utility.set_location('Entering: '||l_proc,10);
1185 --
1186 get_PAB_correction_element (person.due_date);
1187 --
1188 -- Check each existing SaP entry in turn against all the potential new ones.
1189 --
1190 <<OLD_ENTRIES>>
1191 for old_entry in csr_existing_entries
1192 LOOP
1193 --First loop through the hypothetical entries to see if there is one
1194 --which covers the same week as the old entry and is not subject to
1195 --a stoppage. If there isn't one, invalidate the old entry.
1196 --Assume we don't need to correct the entry until we discover otherwise:
1197 --
1198 l_ins_corr_ele := FALSE;
1199 begin
1200 entry_number := 0;
1201 if p_deleting then
1202 raise no_data_found; -- enter exception handler
1203 end if;
1204 LOOP
1205 entry_number := entry_number +1;
1206 -- Exit the loop when we find a hypothetical entry covering the
1207 -- same week as the old entry, which is not subject to a stoppage.
1208 -- If no such match is found, then we will reach the end of the
1209 -- pl/sql table and attempt to read beyond the existing rows; this
1210 -- will cause us to enter the exception handler and indicate that
1211 -- no match was found.
1212 exit when ((old_entry.week_commencing
1213 = hypothetical_entry.week_commencing (entry_number)
1214 and not hypothetical_entry.stopped (entry_number) = 'TRUE'
1215 and ssp_smp_pkg.g_smp_update = 'N')
1216 or (old_entry.effective_start_date
1217 = hypothetical_entry.effective_start_date (entry_number)
1218 and old_entry.week_commencing
1219 = hypothetical_entry.week_commencing (entry_number)
1220 and not hypothetical_entry.stopped (entry_number) = 'TRUE'
1221 and ssp_smp_pkg.g_smp_update = 'Y'));
1222 end loop;
1223 hr_utility.trace (l_proc||' Old entry / Hypo entry time Match with values:');
1224 hr_utility.trace (l_proc||' Rate: ' ||old_entry.rate||' / '
1225 ||hypothetical_entry.rate (Entry_number));
1226 hr_utility.trace (l_proc||' Amount: '
1227 ||old_entry.amount||' / '
1228 ||hypothetical_entry.amount (entry_number));
1229 hr_utility.trace (l_proc||' Recoverable: '
1230 ||old_entry.recoverable_amount||' / '
1231 ||hypothetical_entry.recoverable_amount (entry_number));
1232 hr_utility.trace (l_proc||' Week Comm: '
1233 ||hypothetical_entry.week_commencing (entry_number) );
1234 --A hypo entry covers the same week as the old one
1235 if old_entry.rate = hypothetical_entry.rate (entry_number)
1236 and old_entry.amount = hypothetical_entry.amount(entry_number)
1237 and old_entry.recoverable_amount
1238 = hypothetical_entry.recoverable_amount (entry_number)
1239 then
1240 -- the hypo entry has the same values as the old one
1241 -- don't create a correction element.
1242 -- don't create a new entry
1243 hypothetical_entry.dealt_with (entry_number) := 'TRUE';
1244 hr_utility.trace (l_proc||' leave unchanged');
1245 else
1246 if ssp_smp_support_pkg.entry_already_processed
1247 (old_entry.element_entry_id)
1248 then
1249 l_ins_corr_ele := TRUE;
1250 hr_utility.trace (l_proc||' processed - correct it');
1251 else
1252 -- update old entry
1253 hr_utility.trace (l_proc||' unprocessed - update it');
1254 hr_entry_api.update_element_entry (
1255 p_dt_update_mode => 'CORRECTION',
1256 p_session_date => old_entry.effective_start_date,
1257 p_element_entry_id => old_entry.element_entry_id,
1258 p_input_value_id1 => g_PAB_element.rate_id,
1259 p_input_value_id2 => g_PAB_element.amount_id,
1260 p_input_value_id3 => g_PAB_element.recoverable_amount_id,
1261 p_entry_value1=> hypothetical_entry.rate (entry_number),
1262 p_entry_value2=> hypothetical_entry.amount(entry_number),
1263 p_entry_value3=>
1264 hypothetical_entry.recoverable_amount (entry_number));
1265 --
1266 --prevent insertion of new entry
1267 --
1268 hypothetical_entry.dealt_with (entry_number) := 'TRUE';
1269 end if;
1270 end if;
1271 exception
1272 when no_data_found then
1273 -- There was no new entry which exactly matched the old entry.
1274 -- or we are deleting.
1275 entry_number := null;
1276 hr_utility.trace (l_proc||' No Old entry - Hypo entry time Match');
1277 hr_utility.trace (l_proc||' or p_deleting is true');
1278 hr_utility.trace (l_proc||' Old entry values:');
1279 hr_utility.trace (l_proc||' Rate: '||old_entry.rate);
1280 hr_utility.trace (l_proc||' Amount: '||old_entry.amount);
1281 hr_utility.trace (l_proc||' Recoverable: '
1282 ||old_entry.recoverable_amount);
1283 if ssp_smp_support_pkg.entry_already_processed
1284 (old_entry.element_entry_id)
1285 then l_ins_corr_ele := TRUE;
1286 hr_utility.trace (l_proc||' Old entry already processed');
1287 else
1288 hr_utility.trace (l_proc||' Old entry NOT already processed');
1289 --Old entry not already processed so delete it
1290 hr_entry_api.delete_element_entry (
1291 p_dt_delete_mode => 'ZAP',
1292 p_session_date => old_entry.effective_start_date,
1293 p_element_entry_id => old_entry.element_entry_id);
1294 end if;
1295 end;
1296 if l_ins_corr_ele
1297 then
1298 -- Create a correction element to reverse the old entry. Then create a
1299 -- brand new entry with the correct values.
1300 --
1301 hr_utility.trace (l_proc ||
1302 ' Inserting CORRECTION entry for week commencing ' ||
1303 to_char (old_entry.week_commencing));
1304 hr_utility.trace (l_proc||' Old value / New value:');
1305 if entry_number is null then
1306 hr_utility.trace (l_proc||' Rate: '
1307 ||old_entry.rate||' / NA');
1308 hr_utility.trace (l_proc||' Amount: '
1309 ||old_entry.amount||' / NA');
1310 hr_utility.trace (l_proc||' Recoverable: '
1311 ||old_entry.recoverable_amount||' / NA');
1312 else
1313 hr_utility.trace (l_proc||' Rate: '
1314 ||old_entry.rate||' / '
1315 ||hypothetical_entry.rate (Entry_number));
1316 hr_utility.trace (l_proc||' Amount: '
1317 ||old_entry.amount||' / '
1318 ||hypothetical_entry.amount (entry_number));
1319 hr_utility.trace (l_proc||' Recoverable: '
1320 ||old_entry.recoverable_amount||' /'
1321 ||hypothetical_entry.recoverable_amount (entry_number));
1322 end if;
1323 --
1324 -- Determine the next available period in which to place the
1325 -- correction entry
1326 --
1327 ssp_smp_support_pkg.get_entry_details (
1328 p_date_earned => old_entry.week_commencing,
1329 p_last_process_date => person.final_process_date,
1330 p_person_id => person.person_id,
1331 p_element_type_id => g_PAB_Correction_element.element_type_id,
1332 p_element_link_id => old_entry.element_link_id,
1333 p_assignment_id => old_entry.assignment_id,
1334 p_effective_start_date => old_entry.effective_start_date,
1335 p_effective_end_date => old_entry.effective_end_date,
1336 p_pay_as_lump_sum => person.pay_PAB_as_lump_sum);
1337 --
1338 -- hr_entry_api's take the lookup meanings not the lookup codes.
1339 -- converted rate codes to meanings before calling the
1340 -- api. Later fix made old_entry (csr_existing_entries) return
1341 -- the meaning, so rate passed directly.
1342 --
1343 hr_entry_api.insert_element_entry (
1344 p_effective_start_date=> old_entry.effective_start_date,
1345 p_effective_end_date => old_entry.effective_end_date,
1346 p_element_entry_id => l_dummy,
1347 p_target_entry_id => old_entry.element_entry_id,
1348 p_assignment_id => old_entry.assignment_id,
1349 p_element_link_id => old_entry.element_link_id,
1350 p_creator_type => c_PAB_creator_type,
1351 p_creator_id => p_maternity_id,
1352 p_entry_type => c_PAB_entry_type,
1353 p_input_value_id1=> g_PAB_correction_element.rate_id,
1354 p_input_value_id2=> g_PAB_correction_element.week_commencing_id,
1355 p_input_value_id3=> g_PAB_correction_element.amount_id,
1356 p_input_value_id4=> g_PAB_correction_element.recoverable_amount_id,
1357 p_entry_value1=> old_entry.rate,
1358 -- p_entry_value2=> old_entry.week_commencing,
1359 p_entry_value2 => to_char(old_entry.week_commencing,'DD-MON-YYYY'),
1360 p_entry_value3=> old_entry.amount * -1,
1361 p_entry_value4=> old_entry.recoverable_amount * -1);
1362 --
1363 --New entry will be created by brand_new_entries loop if not p_deleting
1364 end if;
1365 --
1366 end loop old_entries;
1367 --
1368 -- Having been through all the existing entries, we now check that we
1369 -- have dealt with all the newly derived entries by inserting any which
1370 -- were not flagged as dealt with during the above actions.
1371 --
1372 hr_utility.set_location (l_proc,20);
1373 --
1374 <<BRAND_NEW_ENTRIES>>
1375 begin
1376 if p_deleting then
1377 hr_utility.trace('Deleting an absence so don''t insert entries');
1378 else
1379 for new_entry in 1..g_PAB_element.maximum_PPP_weeks LOOP
1380
1381 if (not hypothetical_entry.dealt_with (new_entry) = 'TRUE')
1382 and (not hypothetical_entry.stopped (new_entry) = 'TRUE')
1383 then
1384 hr_entry_api.insert_element_entry (
1385 p_effective_start_date =>
1386 hypothetical_entry.effective_start_date (new_entry),
1387 p_effective_end_date =>
1388 hypothetical_entry.effective_end_date (new_entry),
1389 p_element_entry_id => l_dummy,
1390 p_assignment_id => hypothetical_entry.assignment_id (new_entry),
1391 p_element_link_id => hypothetical_entry.element_link_id (new_entry),
1392 p_creator_type => c_PAB_creator_type,
1393 p_creator_id => p_maternity_id,
1394 p_entry_type => c_PAB_entry_type,
1395 p_input_value_id1 => g_PAB_element.rate_id,
1396 p_input_value_id2 => g_PAB_element.week_commencing_id,
1397 p_input_value_id3 => g_PAB_element.amount_id,
1398 p_input_value_id4 => g_PAB_element.recoverable_amount_id,
1399 p_entry_value1 => hypothetical_entry.rate (new_entry),
1400 -- p_entry_value2 => hypothetical_entry.week_commencing (new_entry),
1401 p_entry_value2 => to_char(hypothetical_entry.week_commencing(new_entry),'DD-MON-YYYY'),
1402 p_entry_value3 => hypothetical_entry.amount (new_entry),
1403 p_entry_value4 =>
1404 hypothetical_entry.recoverable_amount (new_entry));
1405 end if;
1406 end loop brand_new_entries;
1407 end if;
1408 exception
1409 when no_data_found then
1410 --
1411 -- We have run out of hypothetical entries to insert
1412 --
1413 null;
1414 --
1415 end;
1416 --
1417 -- Orphaned stoppages, associated with deleted absence can now be deleted
1418 -- This replaces cross product constraints that are no longer allowed.
1419 --
1420 open csr_no_of_absences;
1421 fetch csr_no_of_absences into l_no_of_absence_periods;
1422 close csr_no_of_absences;
1423 --
1424 if l_no_of_absence_periods = 0 then
1425 remove_stoppages;
1426 end if;
1427 --
1428 hr_utility.set_location(' Leaving: '||l_proc,100);
1429 --
1430 end save_hypothetical_entries;
1431 --
1432 procedure derive_PAB_week (p_week_number in integer) is
1433 --
1434 -- Derive the start and end dates of the week covered by the SAP
1435 -- payment. This is done by finding out how many weeks into the APP
1436 -- we are and finding the offset from the start date.
1437 --
1438 begin
1439 --
1440 hr_utility.set_location ('Entering: ssp_sap_pkg.derive_PAB_week',1);
1441 hr_utility.trace ('Entry number = '||to_char (p_week_number));
1442 --
1443 hypothetical_entry.week_commencing (p_week_number)
1444 := (person.APP_start_date + ((p_week_number -1) * 7));
1445 --
1446 hypothetical_entry.dealt_with (p_week_number) := 'FALSE';
1447 hypothetical_entry.stopped (p_week_number) := 'FALSE';
1448 hypothetical_entry.element_link_id (p_week_number) := null;
1449 hypothetical_entry.assignment_id (p_week_number) := null;
1450 --
1451 hr_utility.trace ('week_commencing = '
1452 ||to_char (hypothetical_entry.week_commencing (p_week_number)));
1453 --
1454 hr_utility.set_location ('Leaving : ssp_sap_pkg.derive_PAB_week',100);
1455 --
1456 end derive_PAB_week;
1457 --
1458 procedure Check_PAB_stoppages (p_week_number in integer) is
1459 --
1460 -- Find any SAP stoppage for the Adoption which overlaps a date range
1461 --
1462 employee_died varchar2 (30) := 'Employee died';
1463 --
1464 cursor csr_stoppages (p_start_date in date, p_end_date in date) is
1465 --
1466 -- Find any non-overridden stoppages
1467 --
1468 select 1
1469 from ssp_stoppages STP,
1470 ssp_withholding_reasons WRE
1471 where stp.override_stoppage <> 'Y'
1472 --
1473 -- and the stoppage ovelaps the period or the stoppage is for
1474 -- death and is prior to the period
1475 --
1476 and ((wre.reason <> employee_died
1477 and stp.withhold_from <= p_end_date
1478 and nvl (stp.withhold_to, hr_general.end_of_time)
1479 >= p_start_date)
1480 --
1481 or (wre.reason = employee_died
1482 and stp.withhold_from < p_start_date))
1483 --
1484 and stp.maternity_id = p_maternity_id
1485 and stp.reason_id = wre.reason_id;
1486 --
1487 l_dummy integer (1);
1488 --
1489 begin
1490 --
1491 hr_utility.set_location ('ssp_sap_pkg.Check_PAB_stoppages',1);
1492 --
1493 hypothetical_entry.stopped (p_week_number) := 'FALSE';
1494 --
1495 --
1496 open csr_stoppages (
1497 hypothetical_entry.week_commencing (p_week_number),
1498 ssp_smp_support_pkg.end_of_week
1499 (hypothetical_entry.week_commencing (p_week_number)));
1500
1501 fetch csr_stoppages into l_dummy;
1502 --
1503 if csr_stoppages%found
1504 then
1505 --
1506 -- There is an overlap between the SAP week and a stoppage so no SAP
1507 -- is payable.
1508 --
1509 hypothetical_entry.stopped (p_week_number) := 'TRUE';
1510 --
1511 hr_utility.trace ('Entry is STOPPED');
1512 --
1513 -- Keep a tally of the number of stopped weeks
1514 --
1515 l_stopped_weeks := l_stopped_weeks +1;
1516 end if;
1517 --
1518 close csr_stoppages;
1519 --
1520 hr_utility.set_location ('ssp_sap_pkg.Check_PAB_stoppages',10);
1521 --
1522 end Check_PAB_stoppages;
1523 --
1524 procedure Calculate_correct_PAB_rate (p_week_number in number) is
1525 --
1526 -- The entry API takes the lookup meanings so we must find
1527 -- the meanings rather than the codes for SAP rates.
1528 --
1529 cursor csr_rate_meaning (p_rate_band varchar2) is
1530 --
1531 select meaning
1532 from hr_lookups
1533 where lookup_type = 'SPP_RATES'
1534 and lookup_code = p_rate_band;
1535 --
1536 begin
1537 --
1538 hr_utility.set_location ('ssp_sap_pkg.Calculate_correct_PAB_rate',1);
1539 --
1540 if l_high_rate is null then
1541 --
1542 -- Get the meanings for the rate bands
1543 --
1544 -- Get the higher rate band
1545 --
1546 open csr_rate_meaning ('STD');
1547 fetch csr_rate_meaning into l_high_rate;
1548 close csr_rate_meaning;
1549
1550 end if;
1551 --
1552 /*
1553 if (p_week_number - l_stopped_weeks)
1554 <= g_SMP_element.period_at_higher_rate
1555 then
1556 hr_utility.set_location ('ssp_smp_pkg.Calculate_correct_SMP_rate',1);
1557 --
1558 -- We have not yet given the employee all their higher rate weeks
1559 --
1560 */
1561 hypothetical_entry.rate (p_week_number) := l_high_rate;
1562 /*
1563 else
1564 hypothetical_entry.rate (p_week_number) := l_low_rate;
1565 end if;
1566 */
1567 --
1568 hr_utility.trace ('PAB Rate = '
1569 ||hypothetical_entry.rate (p_week_number));
1570 --
1571 hr_utility.set_location ('ssp_sap_pkg.Calculate_correct_PAB_rate',10);
1572 --
1573 end Calculate_correct_PAB_rate;
1574 --
1575 procedure Calculate_PAB_amounts (p_week_number in integer, p_APP_start_date in date) is
1576 --
1577 begin
1578 --
1579 hr_utility.set_location('Entering: ssp_sAp_pkg.Calculate_SaP_amounts',1);
1580 --
1581 -- Get the SAP element for each week in case the SAP rate has changed
1582 --
1583 get_PAB_element (hypothetical_entry.week_commencing (p_week_number));
1584 --
1585 hypothetical_entry.amount (p_week_number)
1586 := least (round (
1587 (average_earnings * g_PAB_element.SPP_rate)
1588 + 0.0049,2),
1589 g_PAB_element.STANDARD_RATE);
1590 --
1591 hypothetical_entry.recoverable_amount (p_week_number)
1592 := round (hypothetical_entry.amount (p_week_number)
1593 * g_PAB_element.recovery_rate,2);
1594 --
1595 hr_utility.trace ('PAB amount = '
1596 ||to_char (hypothetical_entry.amount (p_week_number)));
1597 hr_utility.trace ('Recoverable amount = '
1598 ||to_char (hypothetical_entry.recoverable_amount (p_week_number)));
1599 --
1600 hr_utility.set_location('Leaving : ssp_sap_pkg.Calculate_PAB_amounts',100);
1601 --
1602 end calculate_PAB_amounts;
1603 --
1604 procedure check_parameters is
1605 begin
1606 hr_api.mandatory_arg_error (
1607 p_api_name => l_proc,
1608 p_argument => 'maternity_id',
1609 p_argument_value=> p_maternity_id);
1610 --
1611 end check_parameters;
1612 --
1613 begin
1614 --
1615 hr_utility.set_location ('ssp_sap_pkg.generate_payments',1);
1616 --
1617 check_parameters;
1618 --
1619 <<PAB_WEEKS>>
1620 --
1621 if person.APP_start_date is not null then
1622 for week_number in 1..g_PAB_element.maximum_PPP_weeks
1623 LOOP
1624 --
1625 -- Derive hypothetical entries ie those entries which would be applied for a
1626 -- completely new maternity. Store them internally because we must check
1627 -- previously created entries before applying the hypothetical entries to the
1628 -- database.
1629 --
1630 Derive_PAB_week (week_number);
1631 Check_PAB_stoppages (week_number);
1632 Calculate_correct_PAB_rate (week_number);
1633 Calculate_PAB_amounts (week_number, person.APP_start_date);
1634 --
1635 if (hypothetical_entry.stopped (week_number) = 'FALSE') then
1636 --
1637 -- Get the entry details unless the entry has been stopped (in which case
1638 -- we do not need the entry details and errors may occur if we call the
1639 -- procedure; eg the woman's assignment ends)
1640 --
1641 ssp_smp_support_pkg.get_entry_details (
1642 p_date_earned => hypothetical_entry.week_commencing
1643 (week_number),
1644 p_pay_as_lump_sum => person.pay_PAB_as_lump_sum,
1645 p_last_process_date => person.final_process_date,
1646 p_person_id => person.person_id,
1647 p_element_type_id => g_PAB_element.element_type_id,
1648 p_element_link_id => hypothetical_entry.element_link_id
1649 (week_number),
1650 p_assignment_id => hypothetical_entry.assignment_id
1651 (week_number),
1652 p_effective_start_date => hypothetical_entry.effective_start_date
1653 (week_number),
1654 p_effective_end_date => hypothetical_entry.effective_end_date
1655 (week_number));
1656 end if;
1657 end loop PAB_weeks;
1658 end if;
1659 --
1660 Save_hypothetical_entries(p_deleting);
1661 --
1662 end generate_payments;
1663 --
1664 --------------------------------------------------------------------------------
1665 procedure PAB_control (p_maternity_id in number,
1666 p_deleting in boolean default FALSE) is
1667 --
1668 -- p_deleting parameter added to deal with absences being deleted, without
1669 -- maternity being deleted.
1670 --
1671 cursor csr_maternity is
1672 --
1673 -- Find out if the maternity exists
1674 --
1675 select 1
1676 from ssp_maternities
1677 where maternity_id = p_maternity_id;
1678 --
1679 cursor csr_entries is
1680 --
1681 -- Get all element entries associated with a maternity
1682 --
1683 select /*+ ORDERED use_nl(paa,paaf,etype,entry) */
1684 entry.element_entry_id,
1685 entry.effective_start_date
1686 from per_absence_attendances PAA,
1687 per_all_assignments_f PAAF,
1688 pay_element_entries_f entry
1689 where PAA.maternity_id = p_maternity_id
1690 and PAAF.person_id = PAA.person_id
1691 and entry.creator_type = 'M'
1692 and entry.creator_id = p_maternity_id
1693 and entry.assignment_id = paaf.assignment_id;
1694 --
1695 cursor csr_count_absences is
1696 select count(*)
1697 from ssp_maternities mat,
1698 per_absence_attendances ab
1699 where mat.maternity_id = p_maternity_id
1700 and ab.person_id = mat.person_id
1701 and ab.maternity_id = mat.maternity_id;
1702 --
1703 l_count number;
1704 l_dummy number;
1705 l_proc varchar2 (72) := g_package||'PAB_control';
1706 --
1707 begin
1708 --
1709 hr_utility.set_location (l_proc,1);
1710 --
1711 open csr_maternity;
1712 fetch csr_maternity into l_dummy;
1713 --
1714 if csr_maternity%found then
1715 --
1716 -- Recalculate SAP
1717 --
1718 if entitled_to_PAB (p_maternity_id) then
1719 open csr_count_absences;
1720 fetch csr_count_absences into l_count;
1721 close csr_count_absences;
1722 if l_count > 0 then
1723 generate_payments (p_maternity_id, false);
1724 else
1725 generate_payments (p_maternity_id, p_deleting);
1726 end if;
1727 elsif p_deleting then
1728 -- not entitled but deleting absence then
1729 generate_payments (p_maternity_id, p_deleting);
1730 end if;
1731 else
1732 --
1733 -- The maternity may have been deleted. Remove any element entries associated
1734 -- with it (the absences, stoppages and medicals are handled by constraints).
1735 --
1736 for obsolete in csr_entries LOOP
1737 hr_utility.trace (l_proc||' Deleting element entry_id '||
1738 to_char (obsolete.element_entry_id));
1739 hr_utility.trace (l_proc||'-------------------------------------------');
1740 --
1741 hr_entry_api.delete_element_entry (
1742 p_dt_delete_mode => 'ZAP',
1743 p_session_date => obsolete.effective_start_date,
1744 p_element_entry_id => obsolete.element_entry_id);
1745 end loop;
1746 end if;
1747 --
1748 hr_utility.set_location (l_proc,100);
1749 --
1750 end PAB_control;
1751 --------------------------------------------------------------------------------
1752 end ssp_pab_pkg;