@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Fix a hang in fancy date picker for Ye Olde Time Years

Summary:
Fixes T12960. When the user enters a date like "1917", we currently loop ~20 million times.

Instead:

- Be a little more careful about parsing.
- Javascript's default behavior of interpreting "2001-02-31" as "2001-03-03" ("February 31" -> "March 3") already seems reasonable, so just let it do that.

Test Plan:
Verified these behaviors:

- `2017-08-08` - Valid, recent.
- `17-08-08` - Valid, recent.
- `1917-08-08` - Valid, a century ago, no loop.
- `2017-02-31` - "February 31", interpreted as "March 3" by Javascsript, seems reasonable.
- `Quack` - Default, current time.
- `0/0/0`, `0/99/0` - Default, current time.

Reviewers: avivey, chad

Reviewed By: chad

Maniphest Tasks: T12960

Differential Revision: https://secure.phabricator.com/D18383

+36 -24
+9 -9
resources/celerity/map.php
··· 484 484 'rsrc/js/core/behavior-device.js' => 'bb1dd507', 485 485 'rsrc/js/core/behavior-drag-and-drop-textarea.js' => '484a6e22', 486 486 'rsrc/js/core/behavior-error-log.js' => '6882e80a', 487 - 'rsrc/js/core/behavior-fancy-datepicker.js' => 'a9210d03', 487 + 'rsrc/js/core/behavior-fancy-datepicker.js' => 'ecf4e799', 488 488 'rsrc/js/core/behavior-file-tree.js' => '88236f00', 489 489 'rsrc/js/core/behavior-form.js' => '5c54cbf3', 490 490 'rsrc/js/core/behavior-gesture.js' => '3ab51e2c', ··· 633 633 'javelin-behavior-editengine-reorder-fields' => 'b59e1e96', 634 634 'javelin-behavior-error-log' => '6882e80a', 635 635 'javelin-behavior-event-all-day' => 'b41537c9', 636 - 'javelin-behavior-fancy-datepicker' => 'a9210d03', 636 + 'javelin-behavior-fancy-datepicker' => 'ecf4e799', 637 637 'javelin-behavior-global-drag-and-drop' => '960f6a39', 638 638 'javelin-behavior-herald-rule-editor' => '7ebaeed3', 639 639 'javelin-behavior-high-security-warning' => 'a464fe03', ··· 1716 1716 'javelin-uri', 1717 1717 'phabricator-keyboard-shortcut', 1718 1718 ), 1719 - 'a9210d03' => array( 1720 - 'javelin-behavior', 1721 - 'javelin-util', 1722 - 'javelin-dom', 1723 - 'javelin-stratcom', 1724 - 'javelin-vector', 1725 - ), 1726 1719 'a9f88de2' => array( 1727 1720 'javelin-behavior', 1728 1721 'javelin-dom', ··· 2104 2097 'javelin-workflow', 2105 2098 'javelin-dom', 2106 2099 'phabricator-draggable-list', 2100 + ), 2101 + 'ecf4e799' => array( 2102 + 'javelin-behavior', 2103 + 'javelin-util', 2104 + 'javelin-dom', 2105 + 'javelin-stratcom', 2106 + 'javelin-vector', 2107 2107 ), 2108 2108 'edf8a145' => array( 2109 2109 'javelin-behavior',
+27 -15
webroot/rsrc/js/core/behavior-fancy-datepicker.js
··· 287 287 }; 288 288 289 289 function getValidDate() { 290 - var written_date = new Date(value_y, value_m-1, value_d); 290 + var year_int = parseInt(value_y, 10); 291 291 292 - if (isNaN(written_date.getTime())) { 292 + if (isNaN(year_int) || year_int < 0) { 293 293 return new Date(); 294 - } else { 295 - //year 01 should be 2001, not 1901 296 - if (written_date.getYear() < 70) { 297 - value_y += 2000; 298 - written_date = new Date(value_y, value_m-1, value_d); 299 - } 294 + } 300 295 301 - // adjust for a date like February 31 302 - var adjust = 1; 303 - while (written_date.getMonth() !== value_m-1) { 304 - written_date = new Date(value_y, value_m-1, value_d-adjust); 305 - adjust++; 306 - } 296 + // If the user enters "11" for the year, interpret it as "2011" (which 297 + // is almost certainly what they mean) not "1911" (which is the default 298 + // behavior of Javascript). 299 + if (year_int < 70) { 300 + year_int += 2000; 301 + } 307 302 308 - return written_date; 303 + var month_int = parseInt(value_m, 10); 304 + if (isNaN(month_int) || month_int < 1 || month_int > 12) { 305 + return new Date(); 306 + } 307 + 308 + // In Javascript, January is "0", not "1", so adjust the value down. 309 + month_int = month_int - 1; 310 + 311 + var day_int = parseInt(value_d, 10); 312 + if (isNaN(day_int) || day_int < 1 || day_int > 31) { 313 + return new Date(); 309 314 } 315 + 316 + var written_date = new Date(year_int, month_int, day_int); 317 + if (isNaN(written_date.getTime())) { 318 + return new Date(); 319 + } 320 + 321 + return written_date; 310 322 } 311 323 312 324