Have you ever faced a situation where your dates are just gone wild? For example, you could swear that the date in your XML data is 2009-03-01 (March 1st, 2009), but it shows up on your report as 28-FEB-2009!
I have seen several emails the last few months come to the help mailing list with date formatting related questions, that I thought this might be a worthwhile topic for a blog article.
The cause of this, what some call “odd” behavior, is a combination of four things:
- How dates are stored in the XML data
- Whether and how you format dates in the RTF template
- The timezone that you run the report
- And this thing called Coordinated Universal Time known as UTC
If you find the acronym UTC confusing, it’s because it’s a backronym, not an acronym! Long story short, blame it on the French (or the Americans, depending on which side of the Atlantic you are!) You can read all about it here: http://en.wikipedia.org/wiki/Coordinated_Universal_Time.
So…, here is how these four things together can ruin your “date”!
- At run time, BI Publisher server converts dates that you have applied a format mask in your RTF template to the timezone that the report is destined for (the report timezone).
- When you apply a date format mask to a field in your RTF template, BI Publisher expects the incoming dates from the XML data to be in canonical format. That is, YYYY-MM-DDThh:mm:ss+HH:MM, a standard way to represent date and time in reference to UTC. The +HH:MM is the positive or negative difference of the timezone where the data originates from UTC/GMT.
- If the time component and UTC offset is omitted (i.e. the XML date is in the format YYYY-MM-DD), BI Publisher interprets the date as YYYY-MM-DDT00:00:00-00:00 (i.e. midnight GMT).
If you are responsible for generating the data for the report, you don’t need to worry about converting your dates to canonical format. BI publisher will do that automatically for you.
For example, when you issue the query “Select SYSDATE from DUAL” from BI Publisher, it generates the following XML data set:
<ROWSET>
<ROW>
<SYSDATE>2009-06-03T18:44:32.000-07:00</SYSDATE>
</ROW>
</ROWSET>
Of course no one likes to see dates on their report in that format!
Provided, you want dates and time to be converted to the appropriate time zone the report is destined for, the best and most straightforward approach to address that is to apply a format mask to the date field in your RTF template and let BI Publisher take care of the rest.
For information on how and the types of format masks that you can apply to a date field refer to Number and Date Formatting in the product documentation: http://download.oracle.com/docs/cd/E12844_01/doc/bip.1013/e12187/T421739T481157.htm#4535403
You can also view the Formatting Dates demo available in our Demonstration Library on our OTN page. The URL to out demonstration library is:
http://www.oracle.com/technology/products/xml-publisher/demoshelf/shelf.html
Keeping in mind that if you apply a format mask to a date field in your RTF template, it will result in the conversion of dates and times depending on the report timezone, it’s quite normal for a date to roll back or forward by 1 when your run the report!
EXAMPLE 1
If you use <?format-date:SYSDATE;'LONG_TIME'?> in your RTF template, with the following data set:
<ROWSET>
<ROW>
<SYSDATE>2009-06-03T18:44:32.000-07:00</SYSDATE>
</ROW>
</ROWSET>
It will result in these dates displayed on the report:
------------------------------------------------------------------------------------------------------------------------
Report Timezone SYSDATE
------------------------------------------------------------------------------------------------------------------------
[GMT – 07:00] – America/Los _Angeles Wednesday, June 3, 2009 6:44 PM
[GMT + 08:00] – Asia/Singapore Thursday, June 4, 2009 9:44 AM
------------------------------------------------------------------------------------------------------------------------
Think about it, in this example, the value of SYSDATE is the time I am writing this blog article in California, Wednesday 18:44:32 (6:44 PM) PDT on June 3rd. My friend Babar in Singapore, 15 hrs ahead of me, is having his third cup of coffee at 9:44 AM, Thursday morning of Jun 4th! Nothing “odd” about that!
EXAMPLE 2
If instead the XML date in the data is in the format YYYY-MM-DD, as in the following data set,
<ROWSET>
<ROW>
<SYSDATE>2009-06-03</SYSDATE>
</ROW
</ROWSET>
Running the report using the same RTF template as above, it will result in these dates displayed on the report:
-----------------------------------------------------------------------------------------------------------------------
Report Timezone SYSDATE
------------------------------------------------------------------------------------------------------------------------
[GMT – 07:00] – America/Los _Angeles Tuesday, June 2, 2009 5:00 PM
[GMT + 08:00] – Asia/Singapore Wednesday, June 3, 2009 8:00 AM
------------------------------------------------------------------------------------------------------------------------
The same reasoning applies here. BI Publisher interprets the value of SYSDATE to represent Wednesday, June 3, 12 AM GMT. For me, 7 hrs behind during daylight savings time, it’s still June 2, 5:00 PM. And my friend Babar in Singapore has just finished his first cup of coffee on June 3rd!
What if you don’t want dates to be converted based on the report timezone?
One solution to that is to extract dates in the format that you want them to appear on your report and don’t apply a format mask to date fields in the RTF template. Chances are that BI Publisher will ignore the format mask anyway, unless the format that you extract the dates in matches the date part of the canonical format that dates are expected to be in (i.e., YYYY-MM-DD).
To extract dates in a specific format, you can use a TO_CHAR function in the query. For example, "Select TO_CHAR(SYSDATE,’DD/MM/YYYY’) as SYS_DATE from DUAL" will generate the following data set:
<ROWSET>
<ROW>
<SYS_DATE>03/06/2009</SYS_DATE>
</ROW>
</ROWSET>
The other option is to extract dates in the format required by BI Publisher, and specify a timezone in the format mask for the conversion to override the default, which is the report timezone. If you specify a timezone with the same UTC offset as the dates in the XML data, no conversion takes place.
For example, <?format-date:SYSDATE;'LONG';’America/Los_Angeles’?> with the data in EXAMPLE 1, will always result in Wednesday, June 3, 2009 displayed on the report.
On the other hand, <?format-date:SYSDATE;'LONG';’UTC’?> with the data in EXAMPLE 2, will also result in Wednesday, June 3, 2009 displayed on the report.
Conclusion –
If you’d like your “dates” to behave, be nice to them and play by the rules!
Comments (8)
Nikos,
Great post. It reminded me of some date features I noticed in the 10.1.3.4.1 new features documentation: http://download.oracle.com/docs/cd/E12844_01/doc/bip.1013/e14667/toc.htm#BABGDEAC
Basically it allows you to use some date functions in the parameters for your scheduled reports.
Bryan
Posted by Bryan | June 17, 2009 11:23 PM
Posted on June 17, 2009 23:23
BI Publisher output:
-
2009-06-26T10:42:26.164-04:00
2009-6-26 5.42.26.0 -5:0
MESSAGE_TS is from a TIMESTAMP(3) column.
MESSAGE_DATE is from a TIMESTAMP(0) WITH TIME ZONE column.
Why is the output different? And, how can I get the MESSAGE_DATE output with the 'T' in it?
Posted by Ron Morton | June 26, 2009 7:29 AM
Posted on June 26, 2009 07:29
I have questions not related to the topic that you have posted
1) Is there a standard report to list summary of the printing checks, like how many checks are printed for the day /supplier ?
2) Can copies of actual check be printed as void. Is there a standard feature possible?
3) Is it possible to switch between one step and two step publishing
Posted by MD | June 26, 2009 1:55 PM
Posted on June 26, 2009 13:55
When I put these two lines in the code on a report
<?xdoxslt:xdo_format_date($_XDOXSLTCTX, '1913-10-25T12:00:00.000+01:00','DD-MM-YYYY HH24:MI:SS')?>
<?xdoxslt:xdo_format_date($_XDOXSLTCTX, '1913-10-26T12:00:00.000+01:00','DD-MM-YYYY HH24:MI:SS')?>
for result I get
25-10-1913 10:29:40
26-10-1913 11:00:00
As you can see the time part shifts.
This happens with Java 1.4.2 on the server
Java(TM) 2 Runtime Environment, Standard Edition (build 1.4.2_04-b05)
Java HotSpot(TM) Client VM (build 1.4.2_04-b05, mixed mode)
With BI publisher desktop with JDK 1.6 it is ok.
So be aware if you are using format-date function.
Posted by msonsuz | June 29, 2009 8:49 AM
Posted on June 29, 2009 08:49
Hi,
I was facing the same problem in one of my reports, where the time was shifted based on the timezone mentioned in the canonical format.
The requirement for the report was that a short date format should be implemented.
As the developments was done in India and the deployment in another country, I should not hardcode anything in the rtf.
The solution to my issue was to set the locale and the timezone in the BI publisher 'Preferences' link.
Posted by Denu Samson | July 13, 2009 8:55 PM
Posted on July 13, 2009 20:55
HI,
Can anyone tell me what is the default timezone for BI Publisher?
The BI Publiher installed in my system is taking default timezone as GMT-11.00. On what criteria is the timezone taken as default?
Posted by Ranjini | July 21, 2009 12:09 AM
Posted on July 21, 2009 00:09
Hi Everyone,
Just an idea, has anyone tried inserting the Time/Date using MS Word instead of using SYSDATE from sql. I believe the Time/Date will get converted to correct time zone automatically.
Regards
Viju George
Posted by Viju George | August 27, 2009 12:18 AM
Posted on August 27, 2009 00:18
Hi Nikos,
Thank you very much for your post.
It solved my problem.
With
it works perfect. :)
Posted by Juan Diego Ruiz | August 28, 2009 4:19 AM
Posted on August 28, 2009 04:19