Skip to content

Instantly share code, notes, and snippets.

@jacebenson
Created June 20, 2017 20:04
Show Gist options
  • Save jacebenson/0ae881ea157b94366176eef0c2fe9087 to your computer and use it in GitHub Desktop.
Save jacebenson/0ae881ea157b94366176eef0c2fe9087 to your computer and use it in GitHub Desktop.
/******/ (function(modules) { // webpackBootstrap
/******/ // The module cache
/******/ var installedModules = {};
/******/
/******/ // The require function
/******/ function __webpack_require__(moduleId) {
/******/
/******/ // Check if module is in cache
/******/ if(installedModules[moduleId]) {
/******/ return installedModules[moduleId].exports;
/******/ }
/******/ // Create a new module (and put it into the cache)
/******/ var module = installedModules[moduleId] = {
/******/ i: moduleId,
/******/ l: false,
/******/ exports: {}
/******/ };
/******/
/******/ // Execute the module function
/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
/******/
/******/ // Flag the module as loaded
/******/ module.l = true;
/******/
/******/ // Return the exports of the module
/******/ return module.exports;
/******/ }
/******/
/******/
/******/ // expose the modules object (__webpack_modules__)
/******/ __webpack_require__.m = modules;
/******/
/******/ // expose the module cache
/******/ __webpack_require__.c = installedModules;
/******/
/******/ // define getter function for harmony exports
/******/ __webpack_require__.d = function(exports, name, getter) {
/******/ if(!__webpack_require__.o(exports, name)) {
/******/ Object.defineProperty(exports, name, {
/******/ configurable: false,
/******/ enumerable: true,
/******/ get: getter
/******/ });
/******/ }
/******/ };
/******/
/******/ // getDefaultExport function for compatibility with non-harmony modules
/******/ __webpack_require__.n = function(module) {
/******/ var getter = module && module.__esModule ?
/******/ function getDefault() { return module['default']; } :
/******/ function getModuleExports() { return module; };
/******/ __webpack_require__.d(getter, 'a', getter);
/******/ return getter;
/******/ };
/******/
/******/ // Object.prototype.hasOwnProperty.call
/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
/******/
/******/ // __webpack_public_path__
/******/ __webpack_require__.p = "";
/******/
/******/ // Load entry module and return exports
/******/ return __webpack_require__(__webpack_require__.s = 0);
/******/ })
/************************************************************************/
/******/ ([
/* 0 */
/***/ (function(module, exports) {
later = function() {
"use strict";
var later = {
version: "1.2.0"
};
if (!Array.prototype.indexOf) {
Array.prototype.indexOf = function(searchElement) {
"use strict";
if (this == null) {
throw new TypeError();
}
var t = Object(this);
var len = t.length >>> 0;
if (len === 0) {
return -1;
}
var n = 0;
if (arguments.length > 1) {
n = Number(arguments[1]);
if (n != n) {
n = 0;
} else if (n != 0 && n != Infinity && n != -Infinity) {
n = (n > 0 || -1) * Math.floor(Math.abs(n));
}
}
if (n >= len) {
return -1;
}
var k = n >= 0 ? n : Math.max(len - Math.abs(n), 0);
for (;k < len; k++) {
if (k in t && t[k] === searchElement) {
return k;
}
}
return -1;
};
}
if (!String.prototype.trim) {
String.prototype.trim = function() {
return this.replace(/^\s+|\s+$/g, "");
};
}
later.array = {};
later.array.sort = function(arr, zeroIsLast) {
arr.sort(function(a, b) {
return +a - +b;
});
if (zeroIsLast && arr[0] === 0) {
arr.push(arr.shift());
}
};
later.array.next = function(val, values, extent) {
var cur, zeroIsLargest = extent[0] !== 0, nextIdx = 0;
for (var i = values.length - 1; i > -1; --i) {
cur = values[i];
if (cur === val) {
return cur;
}
if (cur > val || cur === 0 && zeroIsLargest && extent[1] > val) {
nextIdx = i;
continue;
}
break;
}
return values[nextIdx];
};
later.array.nextInvalid = function(val, values, extent) {
var min = extent[0], max = extent[1], len = values.length, zeroVal = values[len - 1] === 0 && min !== 0 ? max : 0, next = val, i = values.indexOf(val), start = next;
while (next === (values[i] || zeroVal)) {
next++;
if (next > max) {
next = min;
}
i++;
if (i === len) {
i = 0;
}
if (next === start) {
return undefined;
}
}
return next;
};
later.array.prev = function(val, values, extent) {
var cur, len = values.length, zeroIsLargest = extent[0] !== 0, prevIdx = len - 1;
for (var i = 0; i < len; i++) {
cur = values[i];
if (cur === val) {
return cur;
}
if (cur < val || cur === 0 && zeroIsLargest && extent[1] < val) {
prevIdx = i;
continue;
}
break;
}
return values[prevIdx];
};
later.array.prevInvalid = function(val, values, extent) {
var min = extent[0], max = extent[1], len = values.length, zeroVal = values[len - 1] === 0 && min !== 0 ? max : 0, next = val, i = values.indexOf(val), start = next;
while (next === (values[i] || zeroVal)) {
next--;
if (next < min) {
next = max;
}
i--;
if (i === -1) {
i = len - 1;
}
if (next === start) {
return undefined;
}
}
return next;
};
later.day = later.D = {
name: "day",
range: 86400,
val: function(d) {
return d.D || (d.D = later.date.getDate.call(d));
},
isValid: function(d, val) {
return later.D.val(d) === (val || later.D.extent(d)[1]);
},
extent: function(d) {
if (d.DExtent) return d.DExtent;
var month = later.M.val(d), max = later.DAYS_IN_MONTH[month - 1];
if (month === 2 && later.dy.extent(d)[1] === 366) {
max = max + 1;
}
return d.DExtent = [ 1, max ];
},
start: function(d) {
return d.DStart || (d.DStart = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d)));
},
end: function(d) {
return d.DEnd || (d.DEnd = later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d)));
},
next: function(d, val) {
val = val > later.D.extent(d)[1] ? 1 : val;
var month = later.date.nextRollover(d, val, later.D, later.M), DMax = later.D.extent(month)[1];
val = val > DMax ? 1 : val || DMax;
return later.date.next(later.Y.val(month), later.M.val(month), val);
},
prev: function(d, val) {
var month = later.date.prevRollover(d, val, later.D, later.M), DMax = later.D.extent(month)[1];
return later.date.prev(later.Y.val(month), later.M.val(month), val > DMax ? DMax : val || DMax);
}
};
later.dayOfWeekCount = later.dc = {
name: "day of week count",
range: 604800,
val: function(d) {
return d.dc || (d.dc = Math.floor((later.D.val(d) - 1) / 7) + 1);
},
isValid: function(d, val) {
return later.dc.val(d) === val || val === 0 && later.D.val(d) > later.D.extent(d)[1] - 7;
},
extent: function(d) {
return d.dcExtent || (d.dcExtent = [ 1, Math.ceil(later.D.extent(d)[1] / 7) ]);
},
start: function(d) {
return d.dcStart || (d.dcStart = later.date.next(later.Y.val(d), later.M.val(d), Math.max(1, (later.dc.val(d) - 1) * 7 + 1 || 1)));
},
end: function(d) {
return d.dcEnd || (d.dcEnd = later.date.prev(later.Y.val(d), later.M.val(d), Math.min(later.dc.val(d) * 7, later.D.extent(d)[1])));
},
next: function(d, val) {
val = val > later.dc.extent(d)[1] ? 1 : val;
var month = later.date.nextRollover(d, val, later.dc, later.M), dcMax = later.dc.extent(month)[1];
val = val > dcMax ? 1 : val;
var next = later.date.next(later.Y.val(month), later.M.val(month), val === 0 ? later.D.extent(month)[1] - 6 : 1 + 7 * (val - 1));
if (next.getTime() <= d.getTime()) {
month = later.M.next(d, later.M.val(d) + 1);
return later.date.next(later.Y.val(month), later.M.val(month), val === 0 ? later.D.extent(month)[1] - 6 : 1 + 7 * (val - 1));
}
return next;
},
prev: function(d, val) {
var month = later.date.prevRollover(d, val, later.dc, later.M), dcMax = later.dc.extent(month)[1];
val = val > dcMax ? dcMax : val || dcMax;
return later.dc.end(later.date.prev(later.Y.val(month), later.M.val(month), 1 + 7 * (val - 1)));
}
};
later.dayOfWeek = later.dw = later.d = {
name: "day of week",
range: 86400,
val: function(d) {
return d.dw || (d.dw = later.date.getDay.call(d) + 1);
},
isValid: function(d, val) {
return later.dw.val(d) === (val || 7);
},
extent: function() {
return [ 1, 7 ];
},
start: function(d) {
return later.D.start(d);
},
end: function(d) {
return later.D.end(d);
},
next: function(d, val) {
val = val > 7 ? 1 : val || 7;
return later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d) + (val - later.dw.val(d)) + (val <= later.dw.val(d) ? 7 : 0));
},
prev: function(d, val) {
val = val > 7 ? 7 : val || 7;
return later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d) + (val - later.dw.val(d)) + (val >= later.dw.val(d) ? -7 : 0));
}
};
later.dayOfYear = later.dy = {
name: "day of year",
range: 86400,
val: function(d) {
return d.dy || (d.dy = Math.ceil(1 + (later.D.start(d).getTime() - later.Y.start(d).getTime()) / later.DAY));
},
isValid: function(d, val) {
return later.dy.val(d) === (val || later.dy.extent(d)[1]);
},
extent: function(d) {
var year = later.Y.val(d);
return d.dyExtent || (d.dyExtent = [ 1, year % 4 ? 365 : 366 ]);
},
start: function(d) {
return later.D.start(d);
},
end: function(d) {
return later.D.end(d);
},
next: function(d, val) {
val = val > later.dy.extent(d)[1] ? 1 : val;
var year = later.date.nextRollover(d, val, later.dy, later.Y), dyMax = later.dy.extent(year)[1];
val = val > dyMax ? 1 : val || dyMax;
return later.date.next(later.Y.val(year), later.M.val(year), val);
},
prev: function(d, val) {
var year = later.date.prevRollover(d, val, later.dy, later.Y), dyMax = later.dy.extent(year)[1];
val = val > dyMax ? dyMax : val || dyMax;
return later.date.prev(later.Y.val(year), later.M.val(year), val);
}
};
later.hour = later.h = {
name: "hour",
range: 3600,
val: function(d) {
return d.h || (d.h = later.date.getHour.call(d));
},
isValid: function(d, val) {
return later.h.val(d) === val;
},
extent: function() {
return [ 0, 23 ];
},
start: function(d) {
return d.hStart || (d.hStart = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d)));
},
end: function(d) {
return d.hEnd || (d.hEnd = later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d)));
},
next: function(d, val) {
val = val > 23 ? 0 : val;
var next = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d) + (val <= later.h.val(d) ? 1 : 0), val);
if (!later.date.isUTC && next.getTime() <= d.getTime()) {
next = later.date.next(later.Y.val(next), later.M.val(next), later.D.val(next), val + 1);
}
return next;
},
prev: function(d, val) {
val = val > 23 ? 23 : val;
return later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d) + (val >= later.h.val(d) ? -1 : 0), val);
}
};
later.minute = later.m = {
name: "minute",
range: 60,
val: function(d) {
return d.m || (d.m = later.date.getMin.call(d));
},
isValid: function(d, val) {
return later.m.val(d) === val;
},
extent: function(d) {
return [ 0, 59 ];
},
start: function(d) {
return d.mStart || (d.mStart = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d), later.m.val(d)));
},
end: function(d) {
return d.mEnd || (d.mEnd = later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d), later.m.val(d)));
},
next: function(d, val) {
var m = later.m.val(d), s = later.s.val(d), inc = val > 59 ? 60 - m : val <= m ? 60 - m + val : val - m, next = new Date(d.getTime() + inc * later.MIN - s * later.SEC);
if (!later.date.isUTC && next.getTime() <= d.getTime()) {
next = new Date(d.getTime() + (inc + 120) * later.MIN - s * later.SEC);
}
return next;
},
prev: function(d, val) {
val = val > 59 ? 59 : val;
return later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d) + (val >= later.m.val(d) ? -1 : 0), val);
}
};
later.month = later.M = {
name: "month",
range: 2629740,
val: function(d) {
return d.M || (d.M = later.date.getMonth.call(d) + 1);
},
isValid: function(d, val) {
return later.M.val(d) === (val || 12);
},
extent: function() {
return [ 1, 12 ];
},
start: function(d) {
return d.MStart || (d.MStart = later.date.next(later.Y.val(d), later.M.val(d)));
},
end: function(d) {
return d.MEnd || (d.MEnd = later.date.prev(later.Y.val(d), later.M.val(d)));
},
next: function(d, val) {
val = val > 12 ? 1 : val || 12;
return later.date.next(later.Y.val(d) + (val > later.M.val(d) ? 0 : 1), val);
},
prev: function(d, val) {
val = val > 12 ? 12 : val || 12;
return later.date.prev(later.Y.val(d) - (val >= later.M.val(d) ? 1 : 0), val);
}
};
later.second = later.s = {
name: "second",
range: 1,
val: function(d) {
return d.s || (d.s = later.date.getSec.call(d));
},
isValid: function(d, val) {
return later.s.val(d) === val;
},
extent: function() {
return [ 0, 59 ];
},
start: function(d) {
return d;
},
end: function(d) {
return d;
},
next: function(d, val) {
var s = later.s.val(d), inc = val > 59 ? 60 - s : val <= s ? 60 - s + val : val - s, next = new Date(d.getTime() + inc * later.SEC);
if (!later.date.isUTC && next.getTime() <= d.getTime()) {
next = new Date(d.getTime() + (inc + 7200) * later.SEC);
}
return next;
},
prev: function(d, val, cache) {
val = val > 59 ? 59 : val;
return later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d), later.h.val(d), later.m.val(d) + (val >= later.s.val(d) ? -1 : 0), val);
}
};
later.time = later.t = {
name: "time",
range: 1,
val: function(d) {
return d.t || (d.t = later.h.val(d) * 3600 + later.m.val(d) * 60 + later.s.val(d));
},
isValid: function(d, val) {
return later.t.val(d) === val;
},
extent: function() {
return [ 0, 86399 ];
},
start: function(d) {
return d;
},
end: function(d) {
return d;
},
next: function(d, val) {
val = val > 86399 ? 0 : val;
var next = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d) + (val <= later.t.val(d) ? 1 : 0), 0, 0, val);
if (!later.date.isUTC && next.getTime() < d.getTime()) {
next = later.date.next(later.Y.val(next), later.M.val(next), later.D.val(next), later.h.val(next), later.m.val(next), val + 7200);
}
return next;
},
prev: function(d, val) {
val = val > 86399 ? 86399 : val;
return later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d) + (val >= later.t.val(d) ? -1 : 0), 0, 0, val);
}
};
later.weekOfMonth = later.wm = {
name: "week of month",
range: 604800,
val: function(d) {
return d.wm || (d.wm = (later.D.val(d) + (later.dw.val(later.M.start(d)) - 1) + (7 - later.dw.val(d))) / 7);
},
isValid: function(d, val) {
return later.wm.val(d) === (val || later.wm.extent(d)[1]);
},
extent: function(d) {
return d.wmExtent || (d.wmExtent = [ 1, (later.D.extent(d)[1] + (later.dw.val(later.M.start(d)) - 1) + (7 - later.dw.val(later.M.end(d)))) / 7 ]);
},
start: function(d) {
return d.wmStart || (d.wmStart = later.date.next(later.Y.val(d), later.M.val(d), Math.max(later.D.val(d) - later.dw.val(d) + 1, 1)));
},
end: function(d) {
return d.wmEnd || (d.wmEnd = later.date.prev(later.Y.val(d), later.M.val(d), Math.min(later.D.val(d) + (7 - later.dw.val(d)), later.D.extent(d)[1])));
},
next: function(d, val) {
val = val > later.wm.extent(d)[1] ? 1 : val;
var month = later.date.nextRollover(d, val, later.wm, later.M), wmMax = later.wm.extent(month)[1];
val = val > wmMax ? 1 : val || wmMax;
return later.date.next(later.Y.val(month), later.M.val(month), Math.max(1, (val - 1) * 7 - (later.dw.val(month) - 2)));
},
prev: function(d, val) {
var month = later.date.prevRollover(d, val, later.wm, later.M), wmMax = later.wm.extent(month)[1];
val = val > wmMax ? wmMax : val || wmMax;
return later.wm.end(later.date.next(later.Y.val(month), later.M.val(month), Math.max(1, (val - 1) * 7 - (later.dw.val(month) - 2))));
}
};
later.weekOfYear = later.wy = {
name: "week of year (ISO)",
range: 604800,
val: function(d) {
if (d.wy) return d.wy;
var wThur = later.dw.next(later.wy.start(d), 5), YThur = later.dw.next(later.Y.prev(wThur, later.Y.val(wThur) - 1), 5);
return d.wy = 1 + Math.ceil((wThur.getTime() - YThur.getTime()) / later.WEEK);
},
isValid: function(d, val) {
return later.wy.val(d) === (val || later.wy.extent(d)[1]);
},
extent: function(d) {
if (d.wyExtent) return d.wyExtent;
var year = later.dw.next(later.wy.start(d), 5), dwFirst = later.dw.val(later.Y.start(year)), dwLast = later.dw.val(later.Y.end(year));
return d.wyExtent = [ 1, dwFirst === 5 || dwLast === 5 ? 53 : 52 ];
},
start: function(d) {
return d.wyStart || (d.wyStart = later.date.next(later.Y.val(d), later.M.val(d), later.D.val(d) - (later.dw.val(d) > 1 ? later.dw.val(d) - 2 : 6)));
},
end: function(d) {
return d.wyEnd || (d.wyEnd = later.date.prev(later.Y.val(d), later.M.val(d), later.D.val(d) + (later.dw.val(d) > 1 ? 8 - later.dw.val(d) : 0)));
},
next: function(d, val) {
val = val > later.wy.extent(d)[1] ? 1 : val;
var wyThur = later.dw.next(later.wy.start(d), 5), year = later.date.nextRollover(wyThur, val, later.wy, later.Y);
if (later.wy.val(year) !== 1) {
year = later.dw.next(year, 2);
}
var wyMax = later.wy.extent(year)[1], wyStart = later.wy.start(year);
val = val > wyMax ? 1 : val || wyMax;
return later.date.next(later.Y.val(wyStart), later.M.val(wyStart), later.D.val(wyStart) + 7 * (val - 1));
},
prev: function(d, val) {
var wyThur = later.dw.next(later.wy.start(d), 5), year = later.date.prevRollover(wyThur, val, later.wy, later.Y);
if (later.wy.val(year) !== 1) {
year = later.dw.next(year, 2);
}
var wyMax = later.wy.extent(year)[1], wyEnd = later.wy.end(year);
val = val > wyMax ? wyMax : val || wyMax;
return later.wy.end(later.date.next(later.Y.val(wyEnd), later.M.val(wyEnd), later.D.val(wyEnd) + 7 * (val - 1)));
}
};
later.year = later.Y = {
name: "year",
range: 31556900,
val: function(d) {
return d.Y || (d.Y = later.date.getYear.call(d));
},
isValid: function(d, val) {
return later.Y.val(d) === val;
},
extent: function() {
return [ 1970, 2099 ];
},
start: function(d) {
return d.YStart || (d.YStart = later.date.next(later.Y.val(d)));
},
end: function(d) {
return d.YEnd || (d.YEnd = later.date.prev(later.Y.val(d)));
},
next: function(d, val) {
return val > later.Y.val(d) && val <= later.Y.extent()[1] ? later.date.next(val) : later.NEVER;
},
prev: function(d, val) {
return val < later.Y.val(d) && val >= later.Y.extent()[0] ? later.date.prev(val) : later.NEVER;
}
};
later.fullDate = later.fd = {
name: "full date",
range: 1,
val: function(d) {
return d.fd || (d.fd = d.getTime());
},
isValid: function(d, val) {
return later.fd.val(d) === val;
},
extent: function() {
return [ 0, 3250368e7 ];
},
start: function(d) {
return d;
},
end: function(d) {
return d;
},
next: function(d, val) {
return later.fd.val(d) < val ? new Date(val) : later.NEVER;
},
prev: function(d, val) {
return later.fd.val(d) > val ? new Date(val) : later.NEVER;
}
};
later.modifier = {};
later.modifier.after = later.modifier.a = function(constraint, values) {
var value = values[0];
return {
name: "after " + constraint.name,
range: (constraint.extent(new Date())[1] - value) * constraint.range,
val: constraint.val,
isValid: function(d, val) {
return this.val(d) >= value;
},
extent: constraint.extent,
start: constraint.start,
end: constraint.end,
next: function(startDate, val) {
if (val != value) val = constraint.extent(startDate)[0];
return constraint.next(startDate, val);
},
prev: function(startDate, val) {
val = val === value ? constraint.extent(startDate)[1] : value - 1;
return constraint.prev(startDate, val);
}
};
};
later.modifier.before = later.modifier.b = function(constraint, values) {
var value = values[values.length - 1];
return {
name: "before " + constraint.name,
range: constraint.range * (value - 1),
val: constraint.val,
isValid: function(d, val) {
return this.val(d) < value;
},
extent: constraint.extent,
start: constraint.start,
end: constraint.end,
next: function(startDate, val) {
val = val === value ? constraint.extent(startDate)[0] : value;
return constraint.next(startDate, val);
},
prev: function(startDate, val) {
val = val === value ? value - 1 : constraint.extent(startDate)[1];
return constraint.prev(startDate, val);
}
};
};
later.compile = function(schedDef) {
var constraints = [], constraintsLen = 0, tickConstraint;
for (var key in schedDef) {
var nameParts = key.split("_"), name = nameParts[0], mod = nameParts[1], vals = schedDef[key], constraint = mod ? later.modifier[mod](later[name], vals) : later[name];
constraints.push({
constraint: constraint,
vals: vals
});
constraintsLen++;
}
constraints.sort(function(a, b) {
var ra = a.constraint.range, rb = b.constraint.range;
return rb < ra ? -1 : rb > ra ? 1 : 0;
});
tickConstraint = constraints[constraintsLen - 1].constraint;
function compareFn(dir) {
return dir === "next" ? function(a, b) {
return a.getTime() > b.getTime();
} : function(a, b) {
return b.getTime() > a.getTime();
};
}
return {
start: function(dir, startDate) {
var next = startDate, nextVal = later.array[dir], maxAttempts = 1e3, done;
while (maxAttempts-- && !done && next) {
done = true;
for (var i = 0; i < constraintsLen; i++) {
var constraint = constraints[i].constraint, curVal = constraint.val(next), extent = constraint.extent(next), newVal = nextVal(curVal, constraints[i].vals, extent);
if (!constraint.isValid(next, newVal)) {
next = constraint[dir](next, newVal);
done = false;
break;
}
}
}
if (next !== later.NEVER) {
next = dir === "next" ? tickConstraint.start(next) : tickConstraint.end(next);
}
return next;
},
end: function(dir, startDate) {
var result, nextVal = later.array[dir + "Invalid"], compare = compareFn(dir);
for (var i = constraintsLen - 1; i >= 0; i--) {
var constraint = constraints[i].constraint, curVal = constraint.val(startDate), extent = constraint.extent(startDate), newVal = nextVal(curVal, constraints[i].vals, extent), next;
if (newVal !== undefined) {
next = constraint[dir](startDate, newVal);
if (next && (!result || compare(result, next))) {
result = next;
}
}
}
return result;
},
tick: function(dir, date) {
return new Date(dir === "next" ? tickConstraint.end(date).getTime() + later.SEC : tickConstraint.start(date).getTime() - later.SEC);
},
tickStart: function(date) {
return tickConstraint.start(date);
}
};
};
later.schedule = function(sched) {
if (!sched) throw new Error("Missing schedule definition.");
if (!sched.schedules) throw new Error("Definition must include at least one schedule.");
var schedules = [], schedulesLen = sched.schedules.length, exceptions = [], exceptionsLen = sched.exceptions ? sched.exceptions.length : 0;
for (var i = 0; i < schedulesLen; i++) {
schedules.push(later.compile(sched.schedules[i]));
}
for (var j = 0; j < exceptionsLen; j++) {
exceptions.push(later.compile(sched.exceptions[j]));
}
function getInstances(dir, count, startDate, endDate, isRange) {
var compare = compareFn(dir), loopCount = count, maxAttempts = 1e3, schedStarts = [], exceptStarts = [], next, end, results = [], isForward = dir === "next", lastResult, rStart = isForward ? 0 : 1, rEnd = isForward ? 1 : 0;
startDate = startDate ? new Date(startDate) : new Date();
if (!startDate || !startDate.getTime()) throw new Error("Invalid start date.");
setNextStarts(dir, schedules, schedStarts, startDate);
setRangeStarts(dir, exceptions, exceptStarts, startDate);
while (maxAttempts-- && loopCount && (next = findNext(schedStarts, compare))) {
if (endDate && compare(next, endDate)) {
break;
}
if (exceptionsLen) {
updateRangeStarts(dir, exceptions, exceptStarts, next);
if (end = calcRangeOverlap(dir, exceptStarts, next)) {
updateNextStarts(dir, schedules, schedStarts, end);
continue;
}
}
if (isRange) {
var maxEndDate = calcMaxEndDate(exceptStarts, compare);
end = calcEnd(dir, schedules, schedStarts, next, maxEndDate);
var r = isForward ? [ new Date(Math.max(startDate, next)), end ? new Date(endDate ? Math.min(end, endDate) : end) : undefined ] : [ end ? new Date(endDate ? Math.max(endDate, end.getTime() + later.SEC) : end.getTime() + later.SEC) : undefined, new Date(Math.min(startDate, next.getTime() + later.SEC)) ];
if (lastResult && r[rStart].getTime() === lastResult[rEnd].getTime()) {
lastResult[rEnd] = r[rEnd];
loopCount++;
} else {
lastResult = r;
results.push(lastResult);
}
if (!end) break;
updateNextStarts(dir, schedules, schedStarts, end);
} else {
results.push(isForward ? new Date(Math.max(startDate, next)) : getStart(schedules, schedStarts, next, endDate));
tickStarts(dir, schedules, schedStarts, next);
}
loopCount--;
}
for (var i = 0, len = results.length; i < len; i++) {
var result = results[i];
results[i] = Object.prototype.toString.call(result) === "[object Array]" ? [ cleanDate(result[0]), cleanDate(result[1]) ] : cleanDate(result);
}
return results.length === 0 ? later.NEVER : count === 1 ? results[0] : results;
}
function cleanDate(d) {
if (d instanceof Date && !isNaN(d.valueOf())) {
return new Date(d);
}
return undefined;
}
function setNextStarts(dir, schedArr, startsArr, startDate) {
for (var i = 0, len = schedArr.length; i < len; i++) {
startsArr[i] = schedArr[i].start(dir, startDate);
}
}
function updateNextStarts(dir, schedArr, startsArr, startDate) {
var compare = compareFn(dir);
for (var i = 0, len = schedArr.length; i < len; i++) {
if (startsArr[i] && !compare(startsArr[i], startDate)) {
startsArr[i] = schedArr[i].start(dir, startDate);
}
}
}
function setRangeStarts(dir, schedArr, rangesArr, startDate) {
var compare = compareFn(dir);
for (var i = 0, len = schedArr.length; i < len; i++) {
var nextStart = schedArr[i].start(dir, startDate);
if (!nextStart) {
rangesArr[i] = later.NEVER;
} else {
rangesArr[i] = [ nextStart, schedArr[i].end(dir, nextStart) ];
}
}
}
function updateRangeStarts(dir, schedArr, rangesArr, startDate) {
var compare = compareFn(dir);
for (var i = 0, len = schedArr.length; i < len; i++) {
if (rangesArr[i] && !compare(rangesArr[i][0], startDate)) {
var nextStart = schedArr[i].start(dir, startDate);
if (!nextStart) {
rangesArr[i] = later.NEVER;
} else {
rangesArr[i] = [ nextStart, schedArr[i].end(dir, nextStart) ];
}
}
}
}
function tickStarts(dir, schedArr, startsArr, startDate) {
for (var i = 0, len = schedArr.length; i < len; i++) {
if (startsArr[i] && startsArr[i].getTime() === startDate.getTime()) {
startsArr[i] = schedArr[i].start(dir, schedArr[i].tick(dir, startDate));
}
}
}
function getStart(schedArr, startsArr, startDate, minEndDate) {
var result;
for (var i = 0, len = startsArr.length; i < len; i++) {
if (startsArr[i] && startsArr[i].getTime() === startDate.getTime()) {
var start = schedArr[i].tickStart(startDate);
if (minEndDate && start < minEndDate) {
return minEndDate;
}
if (!result || start > result) {
result = start;
}
}
}
return result;
}
function calcRangeOverlap(dir, rangesArr, startDate) {
var compare = compareFn(dir), result;
for (var i = 0, len = rangesArr.length; i < len; i++) {
var range = rangesArr[i];
if (range && !compare(range[0], startDate) && (!range[1] || compare(range[1], startDate))) {
if (!result || compare(range[1], result)) {
result = range[1];
}
}
}
return result;
}
function calcMaxEndDate(exceptsArr, compare) {
var result;
for (var i = 0, len = exceptsArr.length; i < len; i++) {
if (exceptsArr[i] && (!result || compare(result, exceptsArr[i][0]))) {
result = exceptsArr[i][0];
}
}
return result;
}
function calcEnd(dir, schedArr, startsArr, startDate, maxEndDate) {
var compare = compareFn(dir), result;
for (var i = 0, len = schedArr.length; i < len; i++) {
var start = startsArr[i];
if (start && start.getTime() === startDate.getTime()) {
var end = schedArr[i].end(dir, start);
if (maxEndDate && (!end || compare(end, maxEndDate))) {
return maxEndDate;
}
if (!result || compare(end, result)) {
result = end;
}
}
}
return result;
}
function compareFn(dir) {
return dir === "next" ? function(a, b) {
return !b || a.getTime() > b.getTime();
} : function(a, b) {
return !a || b.getTime() > a.getTime();
};
}
function findNext(arr, compare) {
var next = arr[0];
for (var i = 1, len = arr.length; i < len; i++) {
if (arr[i] && compare(next, arr[i])) {
next = arr[i];
}
}
return next;
}
return {
isValid: function(d) {
return getInstances("next", 1, d, d) !== later.NEVER;
},
next: function(count, startDate, endDate) {
return getInstances("next", count || 1, startDate, endDate);
},
prev: function(count, startDate, endDate) {
return getInstances("prev", count || 1, startDate, endDate);
},
nextRange: function(count, startDate, endDate) {
return getInstances("next", count || 1, startDate, endDate, true);
},
prevRange: function(count, startDate, endDate) {
return getInstances("prev", count || 1, startDate, endDate, true);
}
};
};
later.setTimeout = function(fn, sched) {
var s = later.schedule(sched), t;
if (fn) {
scheduleTimeout();
}
function scheduleTimeout() {
var now = Date.now(), next = s.next(2, now);
if (!next[0]) {
t = undefined;
return;
}
var diff = next[0].getTime() - now;
if (diff < 1e3) {
diff = next[1] ? next[1].getTime() - now : 1e3;
}
if (diff < 2147483647) {
t = setTimeout(fn, diff);
} else {
t = setTimeout(scheduleTimeout, 2147483647);
}
}
return {
isDone: function() {
return !t;
},
clear: function() {
clearTimeout(t);
}
};
};
later.setInterval = function(fn, sched) {
if (!fn) {
return;
}
var t = later.setTimeout(scheduleTimeout, sched), done = t.isDone();
function scheduleTimeout() {
if (!done) {
fn();
t = later.setTimeout(scheduleTimeout, sched);
}
}
return {
isDone: function() {
return t.isDone();
},
clear: function() {
done = true;
t.clear();
}
};
};
later.date = {};
later.date.timezone = function(useLocalTime) {
later.date.build = useLocalTime ? function(Y, M, D, h, m, s) {
return new Date(Y, M, D, h, m, s);
} : function(Y, M, D, h, m, s) {
return new Date(Date.UTC(Y, M, D, h, m, s));
};
var get = useLocalTime ? "get" : "getUTC", d = Date.prototype;
later.date.getYear = d[get + "FullYear"];
later.date.getMonth = d[get + "Month"];
later.date.getDate = d[get + "Date"];
later.date.getDay = d[get + "Day"];
later.date.getHour = d[get + "Hours"];
later.date.getMin = d[get + "Minutes"];
later.date.getSec = d[get + "Seconds"];
later.date.isUTC = !useLocalTime;
};
later.date.UTC = function() {
later.date.timezone(false);
};
later.date.localTime = function() {
later.date.timezone(true);
};
later.date.UTC();
later.SEC = 1e3;
later.MIN = later.SEC * 60;
later.HOUR = later.MIN * 60;
later.DAY = later.HOUR * 24;
later.WEEK = later.DAY * 7;
later.DAYS_IN_MONTH = [ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 ];
later.NEVER = 0;
later.date.next = function(Y, M, D, h, m, s) {
return later.date.build(Y, M !== undefined ? M - 1 : 0, D !== undefined ? D : 1, h || 0, m || 0, s || 0);
};
later.date.nextRollover = function(d, val, constraint, period) {
var cur = constraint.val(d), max = constraint.extent(d)[1];
return (val || max) <= cur || val > max ? new Date(period.end(d).getTime() + later.SEC) : period.start(d);
};
later.date.prev = function(Y, M, D, h, m, s) {
var len = arguments.length;
M = len < 2 ? 11 : M - 1;
D = len < 3 ? later.D.extent(later.date.next(Y, M + 1))[1] : D;
h = len < 4 ? 23 : h;
m = len < 5 ? 59 : m;
s = len < 6 ? 59 : s;
return later.date.build(Y, M, D, h, m, s);
};
later.date.prevRollover = function(d, val, constraint, period) {
var cur = constraint.val(d);
return val >= cur || !val ? period.start(period.prev(d, period.val(d) - 1)) : period.start(d);
};
later.parse = {};
later.parse.cron = function(expr, hasSeconds) {
var NAMES = {
JAN: 1,
FEB: 2,
MAR: 3,
APR: 4,
MAY: 5,
JUN: 6,
JUL: 7,
AUG: 8,
SEP: 9,
OCT: 10,
NOV: 11,
DEC: 12,
SUN: 1,
MON: 2,
TUE: 3,
WED: 4,
THU: 5,
FRI: 6,
SAT: 7
};
var REPLACEMENTS = {
"* * * * * *": "0/1 * * * * *",
"@YEARLY": "0 0 1 1 *",
"@ANNUALLY": "0 0 1 1 *",
"@MONTHLY": "0 0 1 * *",
"@WEEKLY": "0 0 * * 0",
"@DAILY": "0 0 * * *",
"@HOURLY": "0 * * * *"
};
var FIELDS = {
s: [ 0, 0, 59 ],
m: [ 1, 0, 59 ],
h: [ 2, 0, 23 ],
D: [ 3, 1, 31 ],
M: [ 4, 1, 12 ],
Y: [ 6, 1970, 2099 ],
d: [ 5, 1, 7, 1 ]
};
function getValue(value, offset, max) {
return isNaN(value) ? NAMES[value] || null : Math.min(+value + (offset || 0), max || 9999);
}
function cloneSchedule(sched) {
var clone = {}, field;
for (field in sched) {
if (field !== "dc" && field !== "d") {
clone[field] = sched[field].slice(0);
}
}
return clone;
}
function add(sched, name, min, max, inc) {
var i = min;
if (!sched[name]) {
sched[name] = [];
}
while (i <= max) {
if (sched[name].indexOf(i) < 0) {
sched[name].push(i);
}
i += inc || 1;
}
sched[name].sort(function(a, b) {
return a - b;
});
}
function addHash(schedules, curSched, value, hash) {
if (curSched.d && !curSched.dc || curSched.dc && curSched.dc.indexOf(hash) < 0) {
schedules.push(cloneSchedule(curSched));
curSched = schedules[schedules.length - 1];
}
add(curSched, "d", value, value);
add(curSched, "dc", hash, hash);
}
function addWeekday(s, curSched, value) {
var except1 = {}, except2 = {};
if (value === 1) {
add(curSched, "D", 1, 3);
add(curSched, "d", NAMES.MON, NAMES.FRI);
add(except1, "D", 2, 2);
add(except1, "d", NAMES.TUE, NAMES.FRI);
add(except2, "D", 3, 3);
add(except2, "d", NAMES.TUE, NAMES.FRI);
} else {
add(curSched, "D", value - 1, value + 1);
add(curSched, "d", NAMES.MON, NAMES.FRI);
add(except1, "D", value - 1, value - 1);
add(except1, "d", NAMES.MON, NAMES.THU);
add(except2, "D", value + 1, value + 1);
add(except2, "d", NAMES.TUE, NAMES.FRI);
}
s.exceptions.push(except1);
s.exceptions.push(except2);
}
function addRange(item, curSched, name, min, max, offset) {
var incSplit = item.split("/"), inc = +incSplit[1], range = incSplit[0];
if (range !== "*" && range !== "0") {
var rangeSplit = range.split("-");
min = getValue(rangeSplit[0], offset, max);
max = getValue(rangeSplit[1], offset, max) || max;
}
add(curSched, name, min, max, inc);
}
function parse(item, s, name, min, max, offset) {
var value, split, schedules = s.schedules, curSched = schedules[schedules.length - 1];
if (item === "L") {
item = min - 1;
}
if ((value = getValue(item, offset, max)) !== null) {
add(curSched, name, value, value);
} else if ((value = getValue(item.replace("W", ""), offset, max)) !== null) {
addWeekday(s, curSched, value);
} else if ((value = getValue(item.replace("L", ""), offset, max)) !== null) {
addHash(schedules, curSched, value, min - 1);
} else if ((split = item.split("#")).length === 2) {
value = getValue(split[0], offset, max);
addHash(schedules, curSched, value, getValue(split[1]));
} else {
addRange(item, curSched, name, min, max, offset);
}
}
function isHash(item) {
return item.indexOf("#") > -1 || item.indexOf("L") > 0;
}
function itemSorter(a, b) {
return isHash(a) && !isHash(b) ? 1 : a - b;
}
function parseExpr(expr) {
var schedule = {
schedules: [ {} ],
exceptions: []
}, components = expr.replace(/(\s)+/g, " ").split(" "), field, f, component, items;
for (field in FIELDS) {
f = FIELDS[field];
component = components[f[0]];
if (component && component !== "*" && component !== "?") {
items = component.split(",").sort(itemSorter);
var i, length = items.length;
for (i = 0; i < length; i++) {
parse(items[i], schedule, field, f[1], f[2], f[3]);
}
}
}
return schedule;
}
function prepareExpr(expr) {
var prepared = expr.toUpperCase();
return REPLACEMENTS[prepared] || prepared;
}
var e = prepareExpr(expr);
return parseExpr(hasSeconds ? e : "0 " + e);
};
later.parse.recur = function() {
var schedules = [], exceptions = [], cur, curArr = schedules, curName, values, every, modifier, applyMin, applyMax, i, last;
function add(name, min, max) {
name = modifier ? name + "_" + modifier : name;
if (!cur) {
curArr.push({});
cur = curArr[0];
}
if (!cur[name]) {
cur[name] = [];
}
curName = cur[name];
if (every) {
values = [];
for (i = min; i <= max; i += every) {
values.push(i);
}
last = {
n: name,
x: every,
c: curName.length,
m: max
};
}
values = applyMin ? [ min ] : applyMax ? [ max ] : values;
var length = values.length;
for (i = 0; i < length; i += 1) {
var val = values[i];
if (curName.indexOf(val) < 0) {
curName.push(val);
}
}
values = every = modifier = applyMin = applyMax = 0;
}
return {
schedules: schedules,
exceptions: exceptions,
on: function() {
values = arguments[0] instanceof Array ? arguments[0] : arguments;
return this;
},
every: function(x) {
every = x || 1;
return this;
},
after: function(x) {
modifier = "a";
values = [ x ];
return this;
},
before: function(x) {
modifier = "b";
values = [ x ];
return this;
},
first: function() {
applyMin = 1;
return this;
},
last: function() {
applyMax = 1;
return this;
},
time: function() {
for (var i = 0, len = values.length; i < len; i++) {
var split = values[i].split(":");
if (split.length < 3) split.push(0);
values[i] = +split[0] * 3600 + +split[1] * 60 + +split[2];
}
add("t");
return this;
},
second: function() {
add("s", 0, 59);
return this;
},
minute: function() {
add("m", 0, 59);
return this;
},
hour: function() {
add("h", 0, 23);
return this;
},
dayOfMonth: function() {
add("D", 1, applyMax ? 0 : 31);
return this;
},
dayOfWeek: function() {
add("d", 1, 7);
return this;
},
onWeekend: function() {
values = [ 1, 7 ];
return this.dayOfWeek();
},
onWeekday: function() {
values = [ 2, 3, 4, 5, 6 ];
return this.dayOfWeek();
},
dayOfWeekCount: function() {
add("dc", 1, applyMax ? 0 : 5);
return this;
},
dayOfYear: function() {
add("dy", 1, applyMax ? 0 : 366);
return this;
},
weekOfMonth: function() {
add("wm", 1, applyMax ? 0 : 5);
return this;
},
weekOfYear: function() {
add("wy", 1, applyMax ? 0 : 53);
return this;
},
month: function() {
add("M", 1, 12);
return this;
},
year: function() {
add("Y", 1970, 2450);
return this;
},
fullDate: function() {
for (var i = 0, len = values.length; i < len; i++) {
values[i] = values[i].getTime();
}
add("fd");
return this;
},
customModifier: function(id, vals) {
var custom = later.modifier[id];
if (!custom) throw new Error("Custom modifier " + id + " not recognized!");
modifier = id;
values = arguments[1] instanceof Array ? arguments[1] : [ arguments[1] ];
return this;
},
customPeriod: function(id) {
var custom = later[id];
if (!custom) throw new Error("Custom time period " + id + " not recognized!");
add(id, custom.extent(new Date())[0], custom.extent(new Date())[1]);
return this;
},
startingOn: function(start) {
return this.between(start, last.m);
},
between: function(start, end) {
cur[last.n] = cur[last.n].splice(0, last.c);
every = last.x;
add(last.n, start, end);
return this;
},
and: function() {
cur = curArr[curArr.push({}) - 1];
return this;
},
except: function() {
curArr = exceptions;
cur = null;
return this;
}
};
};
later.parse.text = function(str) {
var recur = later.parse.recur, pos = 0, input = "", error;
var TOKENTYPES = {
eof: /^$/,
rank: /^((\d\d\d\d)|([2-5]?1(st)?|[2-5]?2(nd)?|[2-5]?3(rd)?|(0|[1-5]?[4-9]|[1-5]0|1[1-3])(th)?))\b/,
time: /^((([0]?[1-9]|1[0-2]):[0-5]\d(\s)?(am|pm))|(([0]?\d|1\d|2[0-3]):[0-5]\d))\b/,
dayName: /^((sun|mon|tue(s)?|wed(nes)?|thu(r(s)?)?|fri|sat(ur)?)(day)?)\b/,
monthName: /^(jan(uary)?|feb(ruary)?|ma((r(ch)?)?|y)|apr(il)?|ju(ly|ne)|aug(ust)?|oct(ober)?|(sept|nov|dec)(ember)?)\b/,
yearIndex: /^(\d\d\d\d)\b/,
every: /^every\b/,
after: /^after\b/,
before: /^before\b/,
second: /^(s|sec(ond)?(s)?)\b/,
minute: /^(m|min(ute)?(s)?)\b/,
hour: /^(h|hour(s)?)\b/,
day: /^(day(s)?( of the month)?)\b/,
dayInstance: /^day instance\b/,
dayOfWeek: /^day(s)? of the week\b/,
dayOfYear: /^day(s)? of the year\b/,
weekOfYear: /^week(s)?( of the year)?\b/,
weekOfMonth: /^week(s)? of the month\b/,
weekday: /^weekday\b/,
weekend: /^weekend\b/,
month: /^month(s)?\b/,
year: /^year(s)?\b/,
between: /^between (the)?\b/,
start: /^(start(ing)? (at|on( the)?)?)\b/,
at: /^(at|@)\b/,
and: /^(,|and\b)/,
except: /^(except\b)/,
also: /(also)\b/,
first: /^(first)\b/,
last: /^last\b/,
"in": /^in\b/,
of: /^of\b/,
onthe: /^on the\b/,
on: /^on\b/,
through: /(-|^(to|through)\b)/
};
var NAMES = {
jan: 1,
feb: 2,
mar: 3,
apr: 4,
may: 5,
jun: 6,
jul: 7,
aug: 8,
sep: 9,
oct: 10,
nov: 11,
dec: 12,
sun: 1,
mon: 2,
tue: 3,
wed: 4,
thu: 5,
fri: 6,
sat: 7,
"1st": 1,
fir: 1,
"2nd": 2,
sec: 2,
"3rd": 3,
thi: 3,
"4th": 4,
"for": 4
};
function t(start, end, text, type) {
return {
startPos: start,
endPos: end,
text: text,
type: type
};
}
function peek(expected) {
var scanTokens = expected instanceof Array ? expected : [ expected ], whiteSpace = /\s+/, token, curInput, m, scanToken, start, len;
scanTokens.push(whiteSpace);
start = pos;
while (!token || token.type === whiteSpace) {
len = -1;
curInput = input.substring(start);
token = t(start, start, input.split(whiteSpace)[0]);
var i, length = scanTokens.length;
for (i = 0; i < length; i++) {
scanToken = scanTokens[i];
m = scanToken.exec(curInput);
if (m && m.index === 0 && m[0].length > len) {
len = m[0].length;
token = t(start, start + len, curInput.substring(0, len), scanToken);
}
}
if (token.type === whiteSpace) {
start = token.endPos;
}
}
return token;
}
function scan(expectedToken) {
var token = peek(expectedToken);
pos = token.endPos;
return token;
}
function parseThroughExpr(tokenType) {
var start = +parseTokenValue(tokenType), end = checkAndParse(TOKENTYPES.through) ? +parseTokenValue(tokenType) : start, nums = [];
for (var i = start; i <= end; i++) {
nums.push(i);
}
return nums;
}
function parseRanges(tokenType) {
var nums = parseThroughExpr(tokenType);
while (checkAndParse(TOKENTYPES.and)) {
nums = nums.concat(parseThroughExpr(tokenType));
}
return nums;
}
function parseEvery(r) {
var num, period, start, end;
if (checkAndParse(TOKENTYPES.weekend)) {
r.on(NAMES.sun, NAMES.sat).dayOfWeek();
} else if (checkAndParse(TOKENTYPES.weekday)) {
r.on(NAMES.mon, NAMES.tue, NAMES.wed, NAMES.thu, NAMES.fri).dayOfWeek();
} else {
num = parseTokenValue(TOKENTYPES.rank);
r.every(num);
period = parseTimePeriod(r);
if (checkAndParse(TOKENTYPES.start)) {
num = parseTokenValue(TOKENTYPES.rank);
r.startingOn(num);
parseToken(period.type);
} else if (checkAndParse(TOKENTYPES.between)) {
start = parseTokenValue(TOKENTYPES.rank);
if (checkAndParse(TOKENTYPES.and)) {
end = parseTokenValue(TOKENTYPES.rank);
r.between(start, end);
}
}
}
}
function parseOnThe(r) {
if (checkAndParse(TOKENTYPES.first)) {
r.first();
} else if (checkAndParse(TOKENTYPES.last)) {
r.last();
} else {
r.on(parseRanges(TOKENTYPES.rank));
}
parseTimePeriod(r);
}
function parseScheduleExpr(str) {
pos = 0;
input = str;
error = -1;
var r = recur();
while (pos < input.length && error < 0) {
var token = parseToken([ TOKENTYPES.every, TOKENTYPES.after, TOKENTYPES.before, TOKENTYPES.onthe, TOKENTYPES.on, TOKENTYPES.of, TOKENTYPES["in"], TOKENTYPES.at, TOKENTYPES.and, TOKENTYPES.except, TOKENTYPES.also ]);
switch (token.type) {
case TOKENTYPES.every:
parseEvery(r);
break;
case TOKENTYPES.after:
if (peek(TOKENTYPES.time).type !== undefined) {
r.after(parseTokenValue(TOKENTYPES.time));
r.time();
} else {
r.after(parseTokenValue(TOKENTYPES.rank));
parseTimePeriod(r);
}
break;
case TOKENTYPES.before:
if (peek(TOKENTYPES.time).type !== undefined) {
r.before(parseTokenValue(TOKENTYPES.time));
r.time();
} else {
r.before(parseTokenValue(TOKENTYPES.rank));
parseTimePeriod(r);
}
break;
case TOKENTYPES.onthe:
parseOnThe(r);
break;
case TOKENTYPES.on:
r.on(parseRanges(TOKENTYPES.dayName)).dayOfWeek();
break;
case TOKENTYPES.of:
r.on(parseRanges(TOKENTYPES.monthName)).month();
break;
case TOKENTYPES["in"]:
r.on(parseRanges(TOKENTYPES.yearIndex)).year();
break;
case TOKENTYPES.at:
r.on(parseTokenValue(TOKENTYPES.time)).time();
while (checkAndParse(TOKENTYPES.and)) {
r.on(parseTokenValue(TOKENTYPES.time)).time();
}
break;
case TOKENTYPES.and:
break;
case TOKENTYPES.also:
r.and();
break;
case TOKENTYPES.except:
r.except();
break;
default:
error = pos;
}
}
return {
schedules: r.schedules,
exceptions: r.exceptions,
error: error
};
}
function parseTimePeriod(r) {
var timePeriod = parseToken([ TOKENTYPES.second, TOKENTYPES.minute, TOKENTYPES.hour, TOKENTYPES.dayOfYear, TOKENTYPES.dayOfWeek, TOKENTYPES.dayInstance, TOKENTYPES.day, TOKENTYPES.month, TOKENTYPES.year, TOKENTYPES.weekOfMonth, TOKENTYPES.weekOfYear ]);
switch (timePeriod.type) {
case TOKENTYPES.second:
r.second();
break;
case TOKENTYPES.minute:
r.minute();
break;
case TOKENTYPES.hour:
r.hour();
break;
case TOKENTYPES.dayOfYear:
r.dayOfYear();
break;
case TOKENTYPES.dayOfWeek:
r.dayOfWeek();
break;
case TOKENTYPES.dayInstance:
r.dayOfWeekCount();
break;
case TOKENTYPES.day:
r.dayOfMonth();
break;
case TOKENTYPES.weekOfMonth:
r.weekOfMonth();
break;
case TOKENTYPES.weekOfYear:
r.weekOfYear();
break;
case TOKENTYPES.month:
r.month();
break;
case TOKENTYPES.year:
r.year();
break;
default:
error = pos;
}
return timePeriod;
}
function checkAndParse(tokenType) {
var found = peek(tokenType).type === tokenType;
if (found) {
scan(tokenType);
}
return found;
}
function parseToken(tokenType) {
var t = scan(tokenType);
if (t.type) {
t.text = convertString(t.text, tokenType);
} else {
error = pos;
}
return t;
}
function parseTokenValue(tokenType) {
return parseToken(tokenType).text;
}
function convertString(str, tokenType) {
var output = str;
switch (tokenType) {
case TOKENTYPES.time:
var parts = str.split(/(:|am|pm)/), hour = parts[3] === "pm" && parts[0] < 12 ? parseInt(parts[0], 10) + 12 : parts[0], min = parts[2].trim();
output = (hour.length === 1 ? "0" : "") + hour + ":" + min;
break;
case TOKENTYPES.rank:
output = parseInt(/^\d+/.exec(str)[0], 10);
break;
case TOKENTYPES.monthName:
case TOKENTYPES.dayName:
output = NAMES[str.substring(0, 3)];
break;
}
return output;
}
return parseScheduleExpr(str.toLowerCase());
};
return later;
}();
/***/ })
/******/ ]);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment