Convert oracle query to postgresql - sql

I need to convert oracle query to postgresql
(select PK_,
'Statement of Holdings' as NOTIFICATIONNAME_ ,
CASE NOTIFICATIONSSTATUS_
WHEN 'Processed' THEN 'Succeeded'
WHEN 'Processed With Failure' THEN 'Failed'
WHEN 'Impacted' THEN 'Succeeded'
WHEN 'Impact Failed' THEN 'Failed'
WHEN 'Archived' THEN 'Succeeded'
WHEN 'Prepared' THEN 'Running'
ELSE 'Planned'
END as STATUS ,
DIRECTION_,
UPDATEDATE_ as updatedate_,
(to_date('19700101', 'YYYY-MM-DD HH24:MI:SS' ) + (( 1 / 24 / 60 / 60 / 1000) * UPDATEDATE_)) as MODIFICATIONDATE
from atementOfHoldingsNotification_
where (DIRECTION_ is not null) and (updatedate_ > 1609462800000) )
union all
(select PK_,
'Statement of Transactions' as NOTIFICATIONNAME_ ,
CASE NOTIFICATIONSSTATUS_
WHEN 'Processed' THEN 'Succeeded'
WHEN 'Processed With Failure' THEN 'Failed'
WHEN 'Impacted' THEN 'Succeeded'
WHEN 'Impact Failed' THEN 'Failed'
WHEN 'Archived' THEN 'Succeeded'
WHEN 'Prepared' THEN 'Running'
ELSE 'Planned'
END as STATUS ,
DIRECTION_,
UPDATEDATE_ as updatedate_,
(to_date('19700101', 'YYYY-MM-DD HH24:MI:SS' ) + (( 1 / 24 / 60 / 60 / 1000) * UPDATEDATE_)) as MODIFICATIONDATE
from entOfTransactionsNofitication_
where (DIRECTION_ is not null) and (updatedate_ > 1609462800000))
union all
(select PK_,
'Statement of Pending Transactions' as NOTIFICATIONNAME_ ,
CASE NOTIFICATIONSSTATUS_
WHEN 'Processed' THEN 'Succeeded'
WHEN 'Processed With Failure' THEN 'Failed'
WHEN 'Impacted' THEN 'Succeeded'
WHEN 'Impact Failed' THEN 'Failed'
WHEN 'Archived' THEN 'Succeeded'
WHEN 'Prepared' THEN 'Running'
ELSE 'Planned'
END as STATUS ,
DIRECTION_,
UPDATEDATE_ as updatedate_,
I got this issue when i executed:
ERROR: operator does not exist: date + numeric
LINE 4: ..._, (to_date('19700101', 'YYYY-MM-DD HH24:MI:SS' ) + (( 1 / 2...
^
HINT: No operator matches the given name and argument types. You might need to add explicit type casts.
SQL state: 42883
Character: 586

Instead of:
to_date('19700101', 'YYYY-MM-DD HH24:MI:SS' ) + (( 1 / 24 / 60 / 60 / 1000) * UPDATEDATE_
You can use TIMESTAMP and INTERVAL literals:
TIMESTAMP '1970-01-01 00:00:00.000 UTC' + UPDATEDATE_ * INTERVAL '0.001' SECOND
Which works in both Oracle fiddle and PostgreSQL fiddle.

Related

MOD command calling functions

I have two functions, which are working fine. I want to use the MOD or decode command to call the functions with different options but I can't seem to get the code below to work.
Below is my test CASE. Any help would be greatly appreciated. Thanks in advance for your time and expertise.
ALTER SESSION SET NLS_TIMESTAMP_FORMAT = 'DD-MON-YYYY HH24:MI:SS.FF';
ALTER SESSION SET NLS_DATE_FORMAT = 'DD-MON-YYYY HH24:MI:SS'
CREATE OR REPLACE FUNCTION random_timestamp(
p_from IN TIMESTAMP,
p_to IN TIMESTAMP,
p_fraction IN VARCHAR2 DEFAULT 'Y'
) RETURN TIMESTAMP
IS
return_val_y TIMESTAMP := p_from + dbms_random.value () * (p_to - p_from + INTERVAL '1' DAY);
return_val_n TIMESTAMP (0) := return_val_y;
BEGIN
RETURN CASE
WHEN UPPER (SUBSTR (p_fraction, 1, 1)) = 'Y'
THEN return_val_y
ELSE return_val_N
END;
END random_timestamp;
/
CREATE OR REPLACE FUNCTION random_interval(
p_min IN NUMBER,
p_max IN NUMBER,
p_duration IN VARCHAR2,
p_fraction IN VARCHAR2 DEFAULT 'Y'
) RETURN INTERVAL DAY TO SECOND
IS
return_val_y INTERVAL DAY TO SECOND := NUMTODSINTERVAL(DBMS_RANDOM.VALUE(p_min, p_max), p_duration);
return_val_n INTERVAL DAY TO SECOND :=
( EXTRACT(DAY FROM return_val_y) * 24 * 60 * 60
+ EXTRACT(HOUR FROM return_val_y) * 60 * 60
+ EXTRACT(MINUTE FROM return_val_y) * 60
+ FLOOR(EXTRACT(SECOND FROM return_val_y))
) * INTERVAL '1' SECOND;
BEGIN
RETURN CASE
WHEN UPPER (SUBSTR (p_fraction, 1, 1)) = 'Y'
THEN return_val_y
ELSE return_val_N
END;
END random_interval;
/
/* can't get this to work */
SELECT
CASE MOD(LEVEL, 2)
WHEN 0
THEN
random_timestamp(TIMESTAMP '2022-04-01 00:00:00', TIMESTAMP '2022-04-30 00:00:00', 'Y') as ts,
random_interval(1, 10, 'HOUR', 'Y') as invr
ELSE
random_timestamp(TIMESTAMP '2022-04-01 00:00:00', TIMESTAMP '2022-04-30 00:00:00', 'N') as ts,
random_interval(1, 10, 'HOUR', 'N') as invr
END
FROM dual
CONNECT BY level <= 10;
A CASE expression returns a single expression; not multiple expressions. If you want multiple expressions then move the CASE from wrapping both of them (which is wrong) to inside each of the function calls:
SELECT random_timestamp(
TIMESTAMP '2022-04-01 00:00:00',
TIMESTAMP '2022-04-30 00:00:00',
CASE MOD(LEVEL, 2) WHEN 0 THEN 'Y' ELSE 'N' END
) as ts,
random_interval(
1,
10,
'HOUR',
CASE MOD(LEVEL, 2) WHEN 0 THEN 'Y' ELSE 'N' END
) as invr
FROM dual
CONNECT BY level <= 10;
fiddle

Snowflake: Conversion error of an teradata query to snow sql

I have a Teradata query (updated the fields with sample values):
select (case '-' when '-' then '-' ||'04' || ':' ||'00'
else '04' || ':' ||'00'
end (Interval hour to minute)) +
(case
'2400' when '2400' then 24
else 0
end (interval hour));
output : -04:00 (varchar type)
select (case '-' when '-' then '-' ||'04' || ':' ||'00'
else '04' || ':' ||'00'
end (Interval hour to minute)) +
(case
'1835' when '2400' then 24
else 0
end (interval hour));
output: 20:00 (varchar type)
Want to convert the same in snowflake, but the same output value was not able to insert in snowflake varchar column:
SELECT
(CASE SUBSTR(raw_data, 48, 1)
WHEN '-' THEN CONCAT('-' , SUBSTR(raw_data,49,2) , ':' , SUBSTR(raw_data,51,2))
ELSE CONCAT(SUBSTR(raw_data,49,2) , ':' , SUBSTR(raw_data,51,2)) END) +
(CASE SUBSTR(raw_data,40,4) WHEN '2400' THEN 24 ELSE 0 END)
AS COLUMN_1
FROM
(SELECT temp_row.$1 as raw_data from
#JOB_MANAGEMENT.SNOWFALKE (file_format => 'DB.TBL_FILE_FORMAT',
pattern=>'.*/input_file.txt') temp_table) temp;
Sample:
SELECT
(CASE '-' WHEN '-'
THEN CONCAT('-' , '04 , ':' , '00')
ELSE CONCAT('04' , ':' , '00') END) +
(CASE '1825' WHEN '2400' THEN 24 ELSE 0 END)
Output : -04:00 (column type - varchar) -> but throwing error in snowflake.
Numeric value '-04:00' is not recognized
Instead of trying to rewrite query 1:1, this approach focuses on rewriting the logic using TIME_FROM_PARTS:
SELECT
CASE WHEN SUBSTR(raw_data, 48, 1) = '-'
THEN TIME_FROM_PARTS(24-SUBSTR(raw_data,49,2)::INT, SUBSTR(raw_data,51,2)::INT, 0)
ELSE TIME_FROM_PARTS(SUBSTR(raw_data,49,2)::INT, SUBSTR(raw_data,51,2)::INT, 0)
END
FROM ...

Case when time is beween and on weekends

I am trying to do a case when on one of my columns, but the time has to be between two times during the week and different on the weekends. So if sched_time is between 8:30:00 and 14:45:00 during the week (M-F) then 'ABC' else 'DEF'. The sched_time column looks like this 2020-03-27 09:29:00. Here is what I have so far:
SELECT Client_Last_Name,
Client_First_Name,
Sched_Time,
CASE WHEN Sched_time IS BETWEEN '08:30:00' AND '14:45:00'
THEN 'ABC'
ELSE 'DEF'
END
Field_Name,
Recoded_Response,
Dlsequence
FROM DAILY_LOG_CUSTOM_DATA
WHERE SERVICE_NAME = 'Medical'
AND FIELD_CATEGORY = 'Background Information'
AND Field_Name = 'Restraint?'
AND Recoded_Response = 1
And Sched_Time >= TRUNC(SYSDATE + 1, 'IW') - 8 AND
Sched_Time <= TRUNC(SYSDATE + 1, 'IW') - 1
Assuming that SCHED_TIME is of type DATE then you can take advantage of INTERVAL arithmetic:
SELECT Client_Last_Name,
Client_First_Name,
Sched_Time,
CASE
WHEN Sched_time BETWEEN TRUNC(SCHED_TIME) + INTERVAL '8' HOUR + INTERVAL '30' MINUTE
AND TRUNC(SCHED_TIME) + INTERVAL '14' HOUR + INTERVAL '45' MINUTE AND
TO_CHAR(SCHED_TIME, 'DY') IN ('MON', 'TUE', 'WED', 'THU', 'FRI')
THEN 'ABC'
ELSE 'DEF'
END
Field_Name,
Recoded_Response,
Dlsequence
FROM DAILY_LOG_CUSTOM_DATA
WHERE SERVICE_NAME = 'Medical'
AND FIELD_CATEGORY = 'Background Information'
AND Field_Name = 'Restraint?'
AND Recoded_Response = 1
AND Sched_Time >= TRUNC(SYSDATE + 1, 'IW') - 8 AND
Sched_Time <= TRUNC(SYSDATE + 1, 'IW') - 1
You can use to_char(). Assuming English language settings:
CASE WHEN TO_CHAR(Sched_time, 'HH24:MI:SS') BETWEEN '08:30:00' AND '14:45:00' AND
TO_CHAR(Sched_time, 'DY') NOT IN ('SAT', 'SUN')
THEN 'ABC'
ELSE 'DEF'
END
You can adjust this to include international settings, so the value is in English -- or your native language -- if that is preferable.

SQL Error in Casting

I am trying to join date and time fields in order to select the latest status at a certain point in time using the following code...
select max(CONVERT(DATETIME, S.Start_date, 108)
+ ISNULL(STUFF(case when len(S.start_time) < 4 then '0' + S.start_time else S.start_time end,3,0,':'),'23:59') as LATST
, computer_number
, event_key
, exam_key
from CRIS_status S
where cast(Start_date as datetime) <= '17 Jul 2016 23:59:59'
group by computer_number, event_key, exam_key
and i get the following error messgae Msg 242, Level 16, State 3, Line 1...
You are checking Datetime with a Varchar which probably gives error
Try with this...
select max(CONVERT(DATETIME, S.Start_date, 108)
+ ISNULL(STUFF(case when len(S.start_time) < 4 then '0' + S.start_time else S.start_time end,3,0,':'),'23:59') as LATST
, computer_number
, event_key
, exam_key
from CRIS_status S
where cast(Start_date as datetime) <= cast('17 Jul 2016 23:59:59' as datetime)
group by computer_number, event_key, exam_key
Always use unambiguous date format
select max(CONVERT(DATETIME, S.Start_date, 108)
+ ISNULL(STUFF(case when len(S.start_time) < 4 then '0' + S.start_time else S.start_time end,3,0,':')
,'23:59') as LATST
, computer_number
, event_key
, exam_key
from CRIS_status S
where cast(Start_date as datetime) < '20160718'
group by computer_number, event_key, exam_key

Calculate business days between two dates

I tried the following query I got from an earlier question:
SELECT OrderNumber, InstallDate, CompleteDate,
(TRUNC(CompleteDate) - TRUNC(InstallDate) ) +1 -
((((TRUNC(CompleteDate,'D'))-(TRUNC(InstallDate,'D')))/7)*2) -
(CASE WHEN TO_CHAR(InstallDate,'DY','nls_date_language=english')='SUN' THEN 1 ELSE 0 END) -
(CASE WHEN TO_CHAR(CompleteDate,'DY','nls_date_language=english')='SAT' THEN 1 ELSE 0 END) as BusinessDays
FROM Orders
ORDER BY OrderNumber;
But I get an 'ORA-01722 - Invalid Number' error.
What am I doing wrong?
Following is my modified code that I'm having issues with:
select
CASE WHEN a.reqdt=0 THEN to_char('01/01/2010') ELSE TO_CHAR(TO_DATE('01-01-1970','DD-MM-YY') + ( a.reqdt/ 86400000 ), 'MM/DD/YYYY') END AS DT_SENT_TO_VENDOR,
CASE WHEN a.completedt=0 THEN to_char('01/01/2010') ELSE TO_CHAR(TO_DATE('01-01-1970','DD-MM-YY') + ( a.completedt/ 86400000 ), 'MM/DD/YYYY') END AS COMPLETED_DT,
(CASE WHEN a.completedt=0 THEN to_char('01/01/2010') ELSE TO_CHAR(TO_DATE('01-01-1970','DD-MM-YY') + ( a.completedt/ 86400000 ), 'dd-mm-yyyyY') END -
CASE WHEN a.reqdt=0 THEN to_char('01/01/2010') ELSE TO_CHAR(TO_DATE('01-01-1970','DD-MM-YY') + ( a.reqdt/ 86400000 ), 'MM/DD/YYYY') END ) + 1 -
/*(a.completedt - a.reqdt ) + 1 - */
((((TRUNC(a.completedt,'D'))) - (TRUNC(a.reqdt,'D'))/7)*2) -
(CASE WHEN TO_CHAR(a.reqdt,'DY','nls_date_language=american')='SUN' THEN 1 ELSE 0 END) -
(CASE WHEN TO_CHAR(a.completedt,'DY','nls_date_language=american')='SAT' THEN 1 ELSE 0 END) as BusinessDays
from EST_VER a;