PDA

View Full Version : Dates being set back by 1 day



nkezhaya
4 Feb 2012, 10:22 AM
I stumbled on this post: http://stackoverflow.com/questions/9023641/why-does-extjs-subtract-a-day-when-formatting-a-date

Unfortunately, I can't go through and put in a specific parsing algorithm for every single grid/form I have.

Why is it forcing a time zone on the date fields, and how can I get it to stop?

I have a datecolumn, my time zone is -6 (CST), and it always pushes it back a day. For instance, if ExtJS receives "2012-02-02" from the server, it shows "2012-02-01".

nkezhaya
4 Feb 2012, 10:37 AM
src/core/src/util/Format.js:


date: function (v, format) { if (!v) {
return "";
}
if (!Ext.isDate(v)) {
v = new Date(Date.parse(v));
}
return Ext.Date.dateFormat(v, format || Ext.Date.defaultFormat);
}

This is kind of horrific.


Ext.util.Format.date('2012-02-02')
"02/01/2012"

nkezhaya
4 Feb 2012, 6:27 PM
This is really insane:


Ext.util.Format.date('02/04/2012')
"02/04/2012"


Ext.util.Format.date('2012-02-04')
"02/03/2012"

nkezhaya
6 Feb 2012, 3:45 AM
bump

friend
6 Feb 2012, 6:19 AM
According to the API docs, what you're trying to do should work, so it looks to be a bug.

However, when parsing String dates, I use Ext.Date.parse(), then Ext.util.Format.date() for formatting:



var javascriptDateObject = Ext.Date.parse('2012-02-04', 'Y-m-d');
var stringDateFormatted = Ext.util.Format.date(javascriptDateObject, 'm/d/Y');

nkezhaya
6 Feb 2012, 6:23 AM
Well, the problem isn't that I'm parsing them incorrectly, it's that a datecolumn uses Ext.util.Format.date, which parses the dates incorrectly.


Ext.util.Format.date('2012-02-04')
"02/03/2012"


Ext.util.Format.date('02-04-2012')
"02/04/2012"

This may be a bug, but I definitely can't wait fix a fix. Can I override Ext.util.Format the same way I would any other class? Or should I use Ext.apply?

friend
6 Feb 2012, 6:37 AM
Be sure that the Model which backs your grid's Store declares the incoming date format correctly:



Ext.define('MyApp.model.MyModel', {
extend: 'Ext.data.Model',
fields: [
{name: 'someDateField', type: 'date', dateFormat: 'Y-m-d'}
]
});

nkezhaya
6 Feb 2012, 6:43 AM
Ahh! I was desperately hoping the solution would be so simple. Unfortunately, it didn't change anything. :( Thank you for the suggestion.

Programmers in Iceland that only write Icelandic apps are lucky - they don't deal with time zones ever. :)

friend
6 Feb 2012, 9:24 AM
If you would, please post a sample of the JSON used to populate your Store.

Thx.

nkezhaya
6 Feb 2012, 9:30 AM
Sure. Thank you again for taking the time to look at it.

http://jsfiddle.net/AG9KM/1/

Check the console. For me it shows, "02/03/2012". I'm CST (-0600).

friend
6 Feb 2012, 11:51 AM
I think I found the problem; you specified format instead of dateFormat in your 'fields' declaration. Here's your code sample with the correction made, where it now gives the desired effect:



Ext.onReady(function() {

store = new Ext.data.Store({
fields: [
{name: 'testId', type: 'int'},
{name: 'received_on', type: 'date', dateFormat: 'Y-m-d'}
],
data: [ {testId: 1, received_on: '2012-02-04'} ]
});

console.log( Ext.util.Format.date(store.getAt(0).get('received_on')) );
});

nkezhaya
6 Feb 2012, 12:54 PM
I think I found the problem; you specified format instead of dateFormat in your 'fields' declaration. Here's your code sample with the correction made, where it now gives the desired effect:



Ext.onReady(function() {

store = new Ext.data.Store({
fields: [
{name: 'testId', type: 'int'},
{name: 'received_on', type: 'date', dateFormat: 'Y-m-d'}
],
data: [ {testId: 1, received_on: '2012-02-04'} ]
});

console.log( Ext.util.Format.date(store.getAt(0).get('received_on')) );
});


Wow! Awesome!

Do you know how to set this as the default dateFormat for all fields set with type "date"?

friend
7 Feb 2012, 11:32 AM
I don't know of any easy/built-in way of achieving this. You could possibly extend Ext.data.Store and override the constructor to handle this.

nkezhaya
7 Feb 2012, 2:52 PM
Yeah, but then I'd need to go back and change every single Store in my app (there are about 30).

Is there a way to override the Store constructor before any of them are instantiated?

friend
8 Feb 2012, 6:21 AM
This could get fairly nasty, fairly quick as you'll be delving into the guts of ExtJs pretty heavily. Regardless, here's how to globally override functionality of any ExtJs class, using Ext.data.Store for this particular example. Note that you can override multiple methods, if desired. Just separate them with a comma:



Ext.data.Store.override({

/**
* Creates the store.
* @param {Object} config (optional) Config object
*/
constructor: function(config) {
// Clone the config so we don't modify the original config object
config = Ext.Object.merge({}, config);

var me = this,
groupers = config.groupers || me.groupers,
groupField = config.groupField || me.groupField,
proxy,
data;

<...snip...>

}
});

riyaz1074
17 Feb 2012, 9:43 AM
Hi nkezhaya (http://www.sencha.com/forum/member.php?242866-nkezhaya) ,

Your post is really useful. I sent the date from the server in the format of
"private static final SimpleDateFormat sdf2 = new SimpleDateFormat("MM/dd/yyyy");"
Date dt = new Date();
sd1 = sdf2.format(dt);
modelMap.addAttribute("dateStr1", sd1);


and retrieved in the extjs in the format "Ext.util.Format.date('${dateStr1}', "M d, Y"), "

{
text: Ext.util.Format.date('${dateStr1}', "M d, Y"),
flex: 1,
width: 100,
dataIndex: 'col4',
sortable: true,
align: 'right',
renderer: renderCurrency
}
Now it's coming properly. :)