Skip to content

Commit b6fb366

Browse files
committed
Merge pull request #71 from wmde/pad4Year
Pad the year to 4 digits
2 parents 30b78e0 + 882afb8 commit b6fb366

File tree

2 files changed

+136
-27
lines changed

2 files changed

+136
-27
lines changed

src/values/TimeValue.js

Lines changed: 22 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ var PARENT = dv.DataValue;
1010
* @since 0.1
1111
* @licence GNU GPL v2+
1212
* @author H. Snater < mediawiki@snater.com >
13+
* @author Thiemo Mättig
1314
*
1415
* @constructor
1516
*
@@ -28,8 +29,10 @@ var SELF = dv.TimeValue = util.inherit( 'DvTimeValue', PARENT, function( timesta
2829
this._time = {};
2930

3031
try {
31-
var matches = /^([+-]?\d+)-(\d+)-(\d+)T(\d{2}):(\d{2}):(\d{2})Z$/.exec( timestamp );
32-
this._time.year = parseInt( matches[1], 10 );
32+
var matches = /^([-+]?\d+)-(\d+)-(\d+)T(\d{2}):(\d{2}):(\d{2})Z$/.exec( timestamp );
33+
34+
// Strip additional leading zeros from the year, but keep 4 digits.
35+
this._time.year = matches[1].replace( /\b0+(?=\d{4})/, '' );
3336
this._time.month = parseInt( matches[2], 10 );
3437
this._time.day = parseInt( matches[3], 10 );
3538
this._time.hour = parseInt( matches[4], 10 );
@@ -105,7 +108,7 @@ var SELF = dv.TimeValue = util.inherit( 'DvTimeValue', PARENT, function( timesta
105108
* @return {string}
106109
*/
107110
getSortKey: function() {
108-
return this._getTimestamp();
111+
return this._getTimestamp( true );
109112
},
110113

111114
/**
@@ -120,7 +123,7 @@ var SELF = dv.TimeValue = util.inherit( 'DvTimeValue', PARENT, function( timesta
120123
/**
121124
* @since 0.7
122125
*
123-
* @return {number}
126+
* @return {string}
124127
*/
125128
getYear: function() {
126129
return this._time.year;
@@ -193,14 +196,16 @@ var SELF = dv.TimeValue = util.inherit( 'DvTimeValue', PARENT, function( timesta
193196
},
194197

195198
/**
196-
* Returns a YMD-ordered timestamp string resembling ISO 8601.
197199
* @private
198200
*
199-
* @return {string}
201+
* @param {bool} [padYear=false] True if the year should be padded to the maximum length of 16
202+
* digits, false for the default padding to 4 digits.
203+
*
204+
* @return {string} A YMD-ordered timestamp string resembling ISO 8601.
200205
*/
201-
_getTimestamp: function() {
202-
return ( ( this._time.year < 0 ) ? '-' : '+' )
203-
+ pad( this._time.year, 11 ) + '-'
206+
_getTimestamp: function( padYear ) {
207+
return ( this._time.year.charAt( 0 ) === '-' ? '-' : '+' )
208+
+ pad( this._time.year, padYear ? 16 : 4 ) + '-'
204209
+ pad( this._time.month, 2 ) + '-'
205210
+ pad( this._time.day, 2 ) + 'T'
206211
+ pad( this._time.hour, 2 ) + ':'
@@ -328,12 +333,18 @@ SELF.getPrecisionById = function( id ) {
328333
/**
329334
* @ignore
330335
*
331-
* @param {number} number
336+
* @param {number|string} number
332337
* @param {number} digits
333338
* @return {string}
334339
*/
335340
function pad( number, digits ) {
336-
number = String( Math.abs( number ) );
341+
if( typeof number !== 'string' ) {
342+
number = String( number );
343+
}
344+
345+
// Strip sign characters.
346+
number = number.replace( /^[-+]/, '' );
347+
337348
if ( number.length >= digits ) {
338349
return number;
339350
}

tests/src/values/TimeValue.tests.js

Lines changed: 114 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -63,34 +63,132 @@ define( [
6363
},
6464

6565
/**
66-
* Tests the effect of the private pad() function, relevant in getSortKey() and toJSON().
66+
* Tests the effect of the private pad() function, relevant in toJSON() and getSortKey().
6767
*
6868
* @since 0.7
6969
*
7070
* @param {QUnit} assert
7171
*/
7272
testPad: function( assert ) {
7373
var testCases = {
74-
'-123456789012-00-00T00:00:00Z': '-123456789012-00-00T00:00:00Z',
75-
'-12345678901-00-00T00:00:00Z': '-12345678901-00-00T00:00:00Z',
76-
'-1-1-1T01:01:01Z': '-00000000001-01-01T01:01:01Z',
77-
'1-1-1T01:01:01Z': '+00000000001-01-01T01:01:01Z',
78-
'12-00-00T00:00:00Z': '+00000000012-00-00T00:00:00Z',
79-
'1234567890-00-00T00:00:00Z': '+01234567890-00-00T00:00:00Z',
80-
'12345678901-00-00T00:00:00Z': '+12345678901-00-00T00:00:00Z',
81-
'123456789012-00-00T00:00:00Z': '+123456789012-00-00T00:00:00Z',
82-
'1234567890123456-00-00T00:00:00Z': '+1234567890123456-00-00T00:00:00Z'
74+
// Without leading zeros
75+
'-9000000000000000-12-31T23:59:59Z': [
76+
'-9000000000000000-12-31T23:59:59Z',
77+
'-9000000000000000-12-31T23:59:59Z'
78+
],
79+
'-123456789012-00-00T00:00:00Z': [
80+
'-123456789012-00-00T00:00:00Z',
81+
'-0000123456789012-00-00T00:00:00Z'
82+
],
83+
'-12345678901-00-00T00:00:00Z': [
84+
'-12345678901-00-00T00:00:00Z',
85+
'-0000012345678901-00-00T00:00:00Z'
86+
],
87+
'-1234-1-1T01:01:01Z': [
88+
'-1234-01-01T01:01:01Z',
89+
'-0000000000001234-01-01T01:01:01Z'
90+
],
91+
'-123-1-1T01:01:01Z': [
92+
'-0123-01-01T01:01:01Z',
93+
'-0000000000000123-01-01T01:01:01Z'
94+
],
95+
'-12-1-1T01:01:01Z': [
96+
'-0012-01-01T01:01:01Z',
97+
'-0000000000000012-01-01T01:01:01Z'
98+
],
99+
'-1-1-1T01:01:01Z': [
100+
'-0001-01-01T01:01:01Z',
101+
'-0000000000000001-01-01T01:01:01Z'
102+
],
103+
'0-1-1T01:01:01Z': [
104+
'+0000-01-01T01:01:01Z',
105+
'+0000000000000000-01-01T01:01:01Z'
106+
],
107+
'1-1-1T01:01:01Z': [
108+
'+0001-01-01T01:01:01Z',
109+
'+0000000000000001-01-01T01:01:01Z'
110+
],
111+
'12-00-00T00:00:00Z': [
112+
'+0012-00-00T00:00:00Z',
113+
'+0000000000000012-00-00T00:00:00Z'
114+
],
115+
'123-00-00T00:00:00Z': [
116+
'+0123-00-00T00:00:00Z',
117+
'+0000000000000123-00-00T00:00:00Z'
118+
],
119+
'1234-00-00T00:00:00Z': [
120+
'+1234-00-00T00:00:00Z',
121+
'+0000000000001234-00-00T00:00:00Z'
122+
],
123+
'1234567890-00-00T00:00:00Z': [
124+
'+1234567890-00-00T00:00:00Z',
125+
'+0000001234567890-00-00T00:00:00Z'
126+
],
127+
'12345678901-00-00T00:00:00Z': [
128+
'+12345678901-00-00T00:00:00Z',
129+
'+0000012345678901-00-00T00:00:00Z'
130+
],
131+
'123456789012-00-00T00:00:00Z': [
132+
'+123456789012-00-00T00:00:00Z',
133+
'+0000123456789012-00-00T00:00:00Z'
134+
],
135+
'1234567890123456-00-00T00:00:00Z': [
136+
'+1234567890123456-00-00T00:00:00Z',
137+
'+1234567890123456-00-00T00:00:00Z'
138+
],
139+
'9000000000000000-12-31T23:59:59Z': [
140+
'+9000000000000000-12-31T23:59:59Z',
141+
'+9000000000000000-12-31T23:59:59Z'
142+
],
143+
144+
// With leading zeros
145+
'-0900000000000000-12-31T23:59:59Z': [
146+
'-900000000000000-12-31T23:59:59Z',
147+
'-0900000000000000-12-31T23:59:59Z'
148+
],
149+
'-0000000000000123-01-01T01:01:01Z': [
150+
'-0123-01-01T01:01:01Z',
151+
'-0000000000000123-01-01T01:01:01Z'
152+
],
153+
'+0000000000000000-01-01T01:01:01Z': [
154+
'+0000-01-01T01:01:01Z',
155+
'+0000000000000000-01-01T01:01:01Z'
156+
],
157+
'+0000000000000001-01-01T01:01:01Z': [
158+
'+0001-01-01T01:01:01Z',
159+
'+0000000000000001-01-01T01:01:01Z'
160+
],
161+
'+0900000000000000-12-31T23:59:59Z': [
162+
'+900000000000000-12-31T23:59:59Z',
163+
'+0900000000000000-12-31T23:59:59Z'
164+
],
165+
166+
// Year would become 10000000000000000 when parsed as a number
167+
'-9999999999999999-12-31T23:59:59Z': [
168+
'-9999999999999999-12-31T23:59:59Z',
169+
'-9999999999999999-12-31T23:59:59Z'
170+
],
171+
'9999999999999999-12-31T23:59:59Z': [
172+
'+9999999999999999-12-31T23:59:59Z',
173+
'+9999999999999999-12-31T23:59:59Z'
174+
]
83175
};
84176

85-
for( var iso8601 in testCases ) {
86-
var expected = testCases[iso8601],
87-
actual = new dv.TimeValue( iso8601 ).getSortKey();
177+
for( var timestamp in testCases ) {
178+
var timeValue = new dv.TimeValue( timestamp ),
179+
json = timeValue.toJSON().time,
180+
sortKey = timeValue.getSortKey(),
181+
expectedJSON = testCases[timestamp][0],
182+
expectedSortKey = testCases[timestamp][1];
88183

89184
assert.ok(
90-
expected === actual,
91-
'Expected getSortKey() to return "' + expected + '", got "' + actual + '"'
185+
json === expectedJSON,
186+
'Expected toJSON().time to return "' + expectedJSON + '", got "' + json + '"'
187+
);
188+
assert.ok(
189+
sortKey === expectedSortKey,
190+
'Expected getSortKey() to return "' + expectedSortKey + '", got "' + sortKey + '"'
92191
);
93-
94192
}
95193
}
96194

0 commit comments

Comments
 (0)