elliptical-datetime
Version:
Elliptical phrases to handle natural language dates and times
163 lines (137 loc) • 5.05 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.join = join;
exports.negateDuration = negateDuration;
exports.relativeTime = relativeTime;
exports.absoluteTime = absoluteTime;
exports.ambiguousTime = ambiguousTime;
exports.absoluteDate = absoluteDate;
exports.absoluteDay = absoluteDay;
exports.relativeDate = relativeDate;
exports.relativeDay = relativeDay;
exports.validateDay = validateDay;
exports.possibleDates = possibleDates;
exports.timeLessThan = timeLessThan;
var _lodash = require('lodash');
var _lodash2 = _interopRequireDefault(_lodash);
var _moment = require('moment');
var _moment2 = _interopRequireDefault(_moment);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
// combine a the date components of a Date object and the time components of {hour, minute, second}
// date: moment, Date, or {year, month, day}
// time: {hour, minute, second}
// timezoneOffset = new Date().getTimezoneOffset() from the user's system
function join(date, time, timezoneOffset) {
if (timezoneOffset == null) {
return (0, _moment2.default)(date).set(time).toDate();
} else {
const mom = (0, _moment2.default)(date);
const yearComponents = { year: mom.year(), month: mom.month(), date: mom.date() };
return (0, _moment2.default)().utcOffset(-timezoneOffset).set(yearComponents).set(time).toDate();
}
}
function negateDuration(duration) {
return _lodash2.default.mapValues(duration, num => -num);
}
function relativeTime(duration, now) {
const newTime = (0, _moment2.default)(now).add(_moment2.default.duration(duration));
return { hour: newTime.hour(), minute: newTime.minute(), second: newTime.second() };
}
function absoluteTime(absolute) {
return { hour: absolute.hour, minute: absolute.minute || 0, second: absolute.second || 0 };
}
function ambiguousTime(ambiguousTime, ampm) {
// special case for 24:00
if (ambiguousTime.hour === 24 && (ampm || ambiguousTime.minute || ambiguousTime.second)) {
return null;
}
// special case for 0:00
if (ambiguousTime.hour === 0 && ampm) {
return null;
}
let hour = ampmHourToHour(ambiguousTime.hour, ampm);
if (ampm === 'am' && (hour > 12 || hour < 0) || ampm === 'pm' && (hour < 12 || hour > 23)) {
return null;
}
return { hour, minute: ambiguousTime.minute || 0, second: ambiguousTime.second || 0 };
}
function ampmHourToHour(hour, ampm) {
if (ampm) {
if (hour === 12) {
return ampm === 'am' ? 0 : 12;
} else {
return ampm === 'am' ? hour : hour + 12;
}
} else {
if (hour === 24) {
return 0;
} else {
return hour;
}
}
}
// export function coerceAmbiguousTime (ambiguousTime, range) {
// if (_.inRange(ambiguousTime.hour, ...range)) {
// return ambiguousTime
// } else {
// return {hour: ambiguousTime.hour < 12 ? ambiguousTime.hour + 12 : ambiguousTime.hour - 12, minute: ambiguousTime.minute, second: ambiguousTime.second}
// }
// }
function absoluteDate(absolute) {
return (0, _moment2.default)(absolute).toDate();
}
function absoluteDay(absolute) {
return {
month: absolute.month == null ? (0, _moment2.default)().month() : absolute.month,
day: absolute.day == null ? _moment2.default.day() : absolute.day
};
}
function relativeDate(duration, now = {}) {
return (0, _moment2.default)(now).add(_moment2.default.duration(duration)).toDate();
}
function relativeDay(duration, now = {}) {
const newMoment = (0, _moment2.default)(now).year(2010).add(_moment2.default.duration(duration)); // not leap year
return { month: newMoment.month(), day: newMoment.date() };
}
function validateDay({ month, day, year = 2012 } = {}) {
//leap year
if (_lodash2.default.isUndefined(month) || _lodash2.default.isUndefined(day)) return true;
const dateMoment = (0, _moment2.default)({ year, month, day });
return dateMoment.month() === month;
}
function* possibleDates(obj, referenceDate) {
if (obj.date) {
if (obj._ambiguousWeek) {
for (let i of [0, 7, -7, 14, -14]) {
yield (0, _moment2.default)(obj.date).add(i, 'days').toDate();
}
} else if (obj._ambiguousYear) {
if (obj._ambiguousMonth) {
for (let i of [0, 1, -1]) {
for (let j of [0, 1, -1]) {
yield (0, _moment2.default)(obj.date).add(i, 'years').add(j, 'months').toDate();
}
}
} else {
for (let i of [0, 1, -1]) {
yield (0, _moment2.default)(obj.date).add(i, 'years').toDate();
}
}
} else if (obj._ambiguousCentury) {
for (let i of [0, 100, -100]) {
yield (0, _moment2.default)(obj.date).add(i, 'years').toDate();
}
} else {
yield obj.date;
}
} else {
for (let i of [0, 1, -1]) {
yield (0, _moment2.default)(referenceDate).add(i, 'days').toDate();
}
}
}
function timeLessThan(a, b) {
return a.hour < b.hour || a.hour === b.hour && a.minute < b.minute || a.hour === b.hour && a.minute === b.minute && a.second < b.second;
}