CREATE OR REPLACE PACKAGE BODY EFT_NOM.cout_dates IS /** -- Purpose : Date calculation routines -- #version $Revision: 1 $ -- #author $Author: Gilberta $ -- Created : 17/11/2004 10:31:16 */ /* $Header: /Isle Of Grain/database/PLSQL/cout_dates.pck 1 7/01/05 12:54 Gilberta $ Logfile, Revision, Date, Author $Datetime: $ Date and time of last checkin $Modtime: 4/01/05 16:41 $ Date and time of last modification $History: cout_dates.pck $ * * ***************** Version 1 ***************** * User: Gilberta Date: 7/01/05 Time: 12:54 * Created in $/Isle Of Grain/database/PLSQL * Initial Version */ g_c_one_hour CONSTANT NUMBER := 1 / 24; /* FUNCTION this_period_start(p_period_start IN DATE) RETURN DATE IS l_start_date DATE; BEGIN BEGIN SELECT (floor(((p_period_start - (trunc(p_period_start) + (day_offset)))) / period_len) * period_len) + trunc(p_period_start) + (day_offset) AS start_this_period INTO l_start_date FROM (SELECT VALUE * g_c_one_hour AS day_offset FROM v_syco_gas_day_offset) offset ,(SELECT VALUE * g_c_one_hour AS period_len FROM v_syco_standard_period_length) len; EXCEPTION WHEN OTHERS THEN cout_err.report_and_stop; END; RETURN(l_start_date); END this_period_start;*/ FUNCTION convert_gas_day_to_date(p_gas_day IN DATE) RETURN DATE IS l_gas_day DATE := trunc(p_gas_day); l_date DATE; BEGIN /* BEGIN SELECT l_gas_day + offset.day_offset INTO l_date FROM (SELECT VALUE * g_c_one_hour AS day_offset FROM v_syco_gas_day_offset) offset; EXCEPTION WHEN OTHERS THEN cout_err.report_and_stop; END;*/ RETURN(l_date); END convert_gas_day_to_date; FUNCTION convert_date_to_gas_day(p_date IN DATE) RETURN DATE IS l_gas_day DATE; BEGIN -- BEGIN SELECT trunc(p_date - cout_system_configuration.get_configuration_item('GAS_DAY_OFFSET')/24) INTO l_gas_day FROM DUAL; EXCEPTION WHEN OTHERS THEN cout_err.report_and_stop; END; -- RETURN(l_gas_day); -- END convert_date_to_gas_day; /** -- FUNCTION translate_date -- -- Translate a given date from local timestamp to target timestamp -- -- %param p_conv_datetime The date to be converted -- %param p_timeszone_from The timezone we are converting FROM (default g_local_timezone = Europe/Budapest) -- %param p_timezone_to The timezone we are converting TO (default g_target_timezone = GMT) -- -- %return A date converted to the target timezone */ FUNCTION translate_date ( p_conv_datetime IN DATE , p_timezone_from IN VARCHAR2 DEFAULT cout_system_configuration.get_configuration_item('G_LOCAL_TIMEZONE') , p_timezone_to IN VARCHAR2 DEFAULT cout_system_configuration.get_configuration_item('G_TARGET_TIMEZONE') ) RETURN DATE IS BEGIN -- Convert the date RETURN TO_DATE( TO_CHAR( FROM_TZ( TO_TIMESTAMP( TO_CHAR( p_conv_datetime, 'DDMMYYYYHH24MISS' ) , 'DDMMYYYYHH24MISS' ) , p_timezone_from) AT TIME ZONE p_timezone_to , 'DD/MM/YYYY HH24:MI:SS' ) , 'DD/MM/YYYY HH24:MI:SS' ); EXCEPTION WHEN others THEN RAISE; END translate_date; /** -- FUNCTION check_hours_in_gas_day -- -- Returns number of hours for the given gas day -- Required for Daylight Saving checks where the hours in a day can be 23 or 25 -- -- %param p_gas_day The date being checked (This MUST be provided in local time NOT gmt) -- -- %return NUMBER. Number of hours in the given gas day -- -- Note: The gas day given is assumed to be the 6am START of the gas day being checked. */ FUNCTION hours_in_gas_day( p_gas_day IN DATE ) RETURN NUMBER IS l_hours NUMBER := 0; l_temp_date DATE; l_gmt_hour_today NUMBER := -1; l_gmt_hour_yesterday NUMBER := -1; l_gas_day_offset NUMBER; BEGIN l_hours := -1; l_temp_date := TRUNC(p_gas_day + 1); l_gas_day_offset := NVL(cout_system_configuration.get_configuration_item('GAS_DAY_OFFSET'),6); BEGIN SELECT TO_CHAR( translate_date( TRUNC(l_temp_date) + (l_gas_day_offset/24) ), 'HH24' ) INTO l_gmt_hour_today FROM dual; EXCEPTION WHEN others THEN l_gmt_hour_today := -1; END; BEGIN SELECT TO_CHAR( translate_date( TRUNC(l_temp_date) + (l_gas_day_offset/24) - 1 ), 'HH24' ) INTO l_gmt_hour_yesterday FROM dual; EXCEPTION WHEN others THEN l_gmt_hour_yesterday := -1; END; IF l_gmt_hour_today != -1 AND l_gmt_hour_yesterday != -1 THEN IF l_gmt_hour_today = l_gmt_hour_yesterday THEN -- 24 hours today.... l_hours := 24; ELSIF l_gmt_hour_today < l_gmt_hour_yesterday THEN -- 23 Hours in the day..... l_hours := 23; ELSE -- l_gmt_hour_today > l_gmt_hour_yesterday -- 25 Hours in the day..... l_hours := 25; END IF; END IF; RETURN l_hours; END hours_in_gas_day; FUNCTION get_dst_hours(p_gas_day IN DATE) RETURN NUMBER IS -- /* CURSOR cur_dst_period(cp_date_in IN DATE) IS SELECT period_start ,period_end ,changeover_shift ,season FROM dst_periods WHERE cp_date_in BETWEEN period_start AND period_end;*/ -- v_hours NUMBER := 24; v_date DATE; v_month VARCHAR2(3); v_day VARCHAR2(3); v_remainder NUMBER(2); v_dst_changeover_shift NUMBER; -- v_dst_period_start DATE; v_dst_period_end DATE; v_dst_season VARCHAR2(20); -- c_days_in_a_week CONSTANT NUMBER := 7; -- BEGIN -- -- -- v_date := p_gas_day + 1; -- v_month := to_char(p_gas_day ,'MON'); -- v_day := to_char(v_date ,'DY'); -- v_remainder := last_day(p_gas_day) - v_date; -- /* OPEN cur_dst_period(trunc(v_date)); FETCH cur_dst_period INTO v_dst_period_start, v_dst_period_end, v_dst_changeover_shift, v_dst_season; -- IF cur_dst_period%FOUND THEN -- IF trunc(v_date) = trunc(v_dst_period_end) THEN -- v_hours := v_hours + v_dst_changeover_shift; -- ELSE -- v_hours := 24; -- END IF; -- ELSE -- -- Use English DST rules if the DST_PERIODS table doesn't have a period defined for the gas day. -- v_month := to_char(p_gas_day ,'MON'); v_day := to_char(v_date ,'DY'); v_remainder := last_day(p_gas_day) - v_date; -- IF v_day = 'SUN' AND v_remainder < c_days_in_a_week THEN -- IF v_month = 'MAR' THEN -- v_hours := 23; -- ELSIF v_month = 'OCT' THEN -- v_hours := 25; -- END IF; -- END IF; -- END IF; -- CLOSE cur_dst_period; */ -- RETURN v_hours; -- END get_dst_hours; FUNCTION get_hours(p_gas_day IN DATE) RETURN t_int_array AS -- v_int_array t_int_array := t_int_array(); -- v_hour NUMBER; v_how_many NUMBER; -- BEGIN -- -- Set the start hour -- v_hour := cout_system_configuration.get_configuration_item('GAS_DAY_OFFSET'); -- -- Get the number of hours in the gas day -- -- v_how_many := get_dst_hours(p_gas_day); -- FOR v_index IN 1 .. v_how_many LOOP -- v_int_array.EXTEND; -- v_int_array(v_index) := v_hour; -- v_hour := v_hour + 1; -- IF v_hour = 24 THEN -- v_hour := 0; -- END IF; -- IF v_how_many <> 24 AND v_hour = 2 THEN -- v_hour := v_hour + sign(24 - v_how_many); v_how_many := v_how_many + sign(24 - v_how_many); -- END IF; -- END LOOP; -- RETURN v_int_array; -- END get_hours; BEGIN -- Initialization NULL; END cout_dates; /