timestamp conversion for below query - sql

I have these data '2019-12-19T01:39:29.6941632Z' as varchar2 datatype
i have to replace the T and Z and also to convert the datatype to timestamp
I tried this query but won't work
to_timestamp(replace(replace('2019-12-19T01:39:29.6941632Z','T',''),'Z'),'YYYY.MM.DD:HH24:MI:SS')
Please help me

My proposal would be this one:
CAST(TO_TIMESTAMP_TZ('2019-12-19T01:39:29.6941632Z', 'YYYY-MM-DD"T":HH24:MI:SS.FFTZR') AS TIMESTAMP)

As a slight variation on #Wernfried's conversion, since you aren't using the time zone information you can treat the fixed Z as a character literal too, like the fixed T. Then you can use to_timestamp(), and don't need to cast():
TO_TIMESTAMP('2019-12-19T01:39:29.6941632Z', 'YYYY-MM-DD"T"HH24:MI:SS.FF"Z"')
The YYYY, MM, DD, HH24, MI, SS and FF parts of the format mask are as described in the documentation. The "T" and "Z" are character literals so the function knows not to try to interpret them as part of the timestamp value; which means you don't need to remove/replace them. And the overall format mask matches the source string - by default Oracle is forgiving of using the wrong separators (like . instead of -) but it's better to use the correct expected values anyway.
e.g.:
SELECT TO_TIMESTAMP('2019-12-19T01:39:29.6941632Z', 'YYYY-MM-DD"T"HH24:MI:SS.FF"Z"')
FROM DUAL;
19-DEC-19 01.39.29.694163200 AM
(and you can then handle or format the timestamp however you want)

You need to fix the replace(). And use the correct format.
This works:
select to_timestamp(replace(replace('2019-12-19T01:39:29.6941632Z', 'T', ''), 'Z', ''), 'YYYY-MM-DDHH24:MI:SS.FF')
from dual
Here is a db<>fiddle.

Related

Covert ZULU time to PST

I am trying to covert start_time which is in yulu format to pst.
Start_time sample: 2020-02-04T04:36:42:211Z
from_unixtime(unix_timestamp(sub string(start_time,1,17),'yyyy-MM-ddThh:mm:ss.SSSZ),'yyyy-MM-dd hh:mm:ss)
But I am getting output as NULL.
Please help.
Escape T, Z in the string. Note the use of double-quotes for the pattern and T and Z are escaped with a single-quote.
select from_unixtime(unix_timestamp('2020-02-04T04:36:42:211Z',"yyyy-MM-dd'T'HH:mm:ss:SSS'Z'")
,'yyyy-MM-dd HH:mm:ss')
Also, you don't need a substring as you are matching the pattern for the full string.
It is better to use FROM_UTC_TIMESTAMP because UNIX_TIMESTAMP returns seconds, you will lose the millisecond component of your timestamp.
FROM_UTC_TIMESTAMP(UNIX_TIMESTAMP(2020-02-04T04:36:42:211Z, "yyyy-MM-dd'T'hh:mm:ss.SSS'Z'"), 'PST')
Sometime it might possible that because of "T" and "Z" our result get distorted.In that case we can use:
from_utc_timestamp(CONCAT(substring('2020-02-04T04:36:42:211Z',1,10)," ",substring('2020-02-04T04:36:42:211Z',12,12)),'PST')

Replace character with multiple characters

In my application date formats are configurable and it is stored in one of the following formats in the table:
d.m.Y --> represents dd.mm.rrrr
d.m.y --> represents dd.mm.rr
Y.m.d --> represents rrrr.mm.dd
y.m.d --> represents rr.mm.dd
I need to use it in my queries and procedures to show the dates in the format specified by user which can be done by TO_CHAR(any_date, date_format)
but, I will need to convert these values to the format that Oracle can recognize.
Currently, I am using REPLACE to achieve this as follows:
TO_CHAR(<my_date_column>, REPLACE(
REPLACE(
REPLACE(
REPLACE('<date_format>',
'd', 'dd'),
'm', 'mm'),
'Y', 'rrrr'),
'y', 'rr'))
I am curious to know if there is another way of doing the same. May be using REGEXP_REPLACE or some other way.
Are there any other possible formats then the 4 you listed in your question?
If not that the decode of VBokšić is a valid answer.
Your replace is just as hardcoded.
I suggest to not store the format the user entered at all (neither the text value 19.09.19 nor the used format dd.mm.rr): let the user interface handle the interpretation and store a real DATE. Split your API from your data model.
Would use of decode be an option for you?
TO_CHAR(<my_date_column>, decode(<date_format>, 'd.m.Y', 'dd.mm.rrrr'
, 'd.m.y', 'dd.mm.rr'
, 'Y.m.d', 'rrrr.mm.dd'
, 'y.m.d', 'rr.mm.dd'))
You should start by looking at the definition of the column in the table. Is it a Date type field, a Number field, a varchar2 field?
If any_date is in Date format, then you can just use to_char:
to_char(any_date, 'd.m.Y')
if the field,any_date is in number(8,0) format, then, you need to understand the number format and translate it to char. Suppose any_date is a number as YYYYMMDD, then
use to_char(any_date) to get the number as YYYYMMDD.
If any_date is in number format as YYYYMMDD, and you want it as d.m.Y, then, your best bet is to convert the number to char, then convert to date, then convert back to character:
to_char(to_date(to_char(any_date), 'YYYYMMDD), 'd.m.Y')
If you date is in varchar2 format, then again, the best option is to convert to date format and convert back to varchar2:
to_char(to_date(any_date, ''), '')

Using COALESCE with different data types?

I have a query using COALESCE(timestamp_type::date,charachter_varying) which fails due to the mismatched data types:
ERROR: COALESCE types date and character varying cannot be matched
It works if i cast the timestamp as text:
COALESCE(timestamp_type::text,charachter_varying)
However, now it is returning the full timestamp when I only want YYYY-MM-DD (instead of the full timestamp, YYYY-MM-DD HH:MM:SS.000000+00)
How can I use COALESCE and return only the date portion of the timestamp?
You can use to_char to convert the timestamp using appropriate format mask:
COALESCE(to_char(timestamp_type, 'YYYY-MM-DD'), varchar_col)
The correct casting would be
COALESCE(timestamp_type::date::text,char_var)
This should work as you expect ... if you have the ISO datestyle. But it's MUCH better to not rely on datestyle settings for converting date-times to/from text. Hence, #Gurwinder Singh's answer is the way to go.

Modify an existing to_char date format

Oracle SQL automatically converts my field D.START_DT to the following format:
TO_CHAR(D.START_DT,'YYYY-MM-DD')
Which makes it difficult for me to modify my own date format.
I've tried wrapping another TO_CHAR around it with no luck.
TO_CHAR(TO_CHAR(D.START_DT,'YYYY-MM-DD'), 'MM/DD')
And I've tried SUBSTR to select certain characters, with no luck. I think the hyphen is getting int he way.
SUBSTR(TO_CHAR(D.START_DT,'YYYY-MM-DD'), 6, 7) || '/' || SUBSTR(TO_CHAR(D.START_DT,'YYYY-MM-DD'), 9, 10)
What is the work around for this?
I agree with RMAN Express and see no problems converting dates to any format you need...
In case you still have problems try this (first to_char() in outer query is optional):
SELECT to_char(to_date(some_date, 'YYYY-MM-DD'), 'MM/DD') final_date
FROM
(
SELECT TO_CHAR(SYSDATE,'YYYY-MM-DD') some_date -- this is your "auto converted" date
FROM dual
)
/
A DATE datatype has no format. When you see a date printed on a screen, there was something that APPLIED the format you see. Could be a "default" in the program you are using (like SQL Developer) or your NLS setting, etc. But, a DATE datatype has no format. So, you have complete control over the format you see on screen.
The simplest is to use the TO_CHAR function:
select TO_CHAR(D.START_DT,'YYYY') from dual;
returns just the four digit year.
See TO_CHAR date format options.
http://docs.oracle.com/cd/E11882_01/server.112/e26088/sql_elements004.htm#CDEHIFJA
You should always supply the format in your code and not rely on some other "default" to supply it.

Errors while trying to cast/convert VARCHAR to DATETIME in ANSI SQL

I have a column in a table where timestamps have been stored in VARCHAR format, but I need to compare these against a column of DATETIME values from another table to find time intervals, so I want to either cast or convert the VARCHAR timestamps to DATETIME. However, both casting and converting are giving me problems.
The format of the VARCHAR timestamp looks like this: "29/07/2012 01:53:36 +12".
Using the query:
SELECT CAST(event_timestamp AS datetime) FROM the_table
produces ERROR: date/time field value out of range: "29/07/2012 01:53:36 +12".
Using the query:
SELECT CONVERT(datetime, event_timestamp, 131) from the_table;
produces
ERROR: syntax error at or near ","
LINE 1: select CONVERT(datetime, event_timestamp, 131) from the_tab...
^ (note: this is pointing at the first comma).
The error with CONVERT actually happens even if you use a generic function such as getdate() for the data source. This db uses ANSI SQL-92 (or so I'm told). Could anyone please help me out with this?
This seems really painful, but the following should work:
select dateadd(hh, cast(right(tv, 3) as int),
CONVERT(datetime, left(tv, 10), 103)+CONVERT(datetime, substring(tv, 12, 8), 108)
)
from (select '29/07/2012 01:53:36 +12' as tv) t
I've never added datetime's before, but this just worked on SQL Server 2008.
Why can't SQL Server just support a flexible notation built around yyyy, mm, mmm, dd and so on?
The actual database is Aster Data, which is based on Postgres (as are most recent database engines). In this database, you would use to_timestamp(). See the documentation here http://www.postgresql.org/docs/8.2/static/functions-formatting.html. The call would be something like:
to_timestamp(val, 'MM/DD/YYYY HH:MI:SS tz') -- not sure if this gets the +12
There are no ANSI functions for date conversion, so each database does its own. Even string functions vary among databases (substr? substring? charindex? instr? location?), so there is no ANSI way to do this.
You are using the wrong syntax, try:
CONVERT(varchar(X), datetimeValue, 131)
Where X is the total number of characters desired.
You will then be able to search for a match with datetimeValue and event_timestamp, assuming each value share the same structure. This will allow you to match string against string.
If I'm not mistaken the standard (ANSI SQL) CAST operator always expect time/date/timstamp literals in ISO format ('YYYY-MM-DD')
But according to the manual for Teradata V12 (can't test it), the format of the CAST operator is
CAST(character_expression AS TIMESTAMP timestamp_data_attribute)
with date_data_attribute being a character value plus an optional FORMAT specifier.
So in your case this would probably be:
cast(event_timestamp AS TIMESTAMP FORMAT 'MM/DD/YYYY HH:MI:SS Z');
I'm not entirely sure about the format definition though. You'll probably need to adjust that
Btw: CONVERT isn't a standard SQL function. It's SQL Server specific.