UNPKG

gcl

Version:

码农村nodejs类库,完成解决回调陷阱,配置框架,IOC框架,统一多DB访问框架,可扩展日志框架和io/db/net/thread/pool 克隆表达式,加解密算法等等一系列基础类库和算法的实现

800 lines (741 loc) 26.3 kB
//使用require('cron-parser')进行封装 import V from '../common/tool'; /// <summary> /// 用于分别获取年/月/星期/日/时/分/秒实现 /// </summary> class IDateTimePart { constructor(name) { this.name = name; } GetTime(time) {} GetMaxDate(time) {} AddTime(time, data) {} } /// <summary> /// 年 /// </summary> class YearDateTimePart extends IDateTimePart { constructor() { super('YearDateTimePart'); } GetTime(time) { return time.getFullYear(); } GetMaxDate(time) { return 10000; } AddTime(time, data) { return time.add('y', data); } } /// <summary> /// 星期 /// </summary> class WeekDateTimePart extends IDateTimePart { constructor() { super('WeekDateTimePart'); } GetTime(time) { return time.getDay(); } GetMaxDate(time) { //limit=new Date(time.getFullYear(), time.getMonth() + 1, 1).add('d', -1).getDate(); //return (limit - time.getDate() < 7) ? (limit - time.getDate() + GetTime(time)) : 6; return 7; } AddTime(time, data) { return time.add('d', data); } } /// <summary> /// 月 /// </summary> class MonthDateTimePart extends IDateTimePart { constructor() { super('MonthDateTimePart'); } GetTime(time) { return time.getMonth() + 1; } GetMaxDate(time) { return 12; } AddTime(time, data) { return time.add('m', data); } } /// <summary> /// 日 /// </summary> class DayDateTimePart extends IDateTimePart { constructor() { super('DayDateTimePart'); } GetTime(time) { return time.getDate(); } GetMaxDate(time = new Date()) { return new Date(time.getFullYear(), time.getMonth() + 1, 1).add('d', -1).getDate(); } AddTime(time, data) { return time.add('d', data); } } /// <summary> /// 时 /// </summary> class HourDateTimePart extends IDateTimePart { constructor() { super('HourDateTimePart'); } GetTime(time) { return time.getHours(); } GetMaxDate(time) { return 24; } AddTime(time, data) { return time.add('h', data); } } /// <summary> /// 分 /// </summary> class MinuteDateTimePart extends IDateTimePart { constructor() { super('MinuteDateTimePart'); } GetTime(time) { return time.getMinutes(); } GetMaxDate(time) { return 60; } AddTime(time, data) { return time.add('n', data); } } /// <summary> /// 秒 /// </summary> class SecondDateTimePart extends IDateTimePart { constructor() { super('SecondDateTimePart'); } GetTime(time) { return time.getSeconds(); } GetMaxDate(time) { return 60; } AddTime(time, data) { return time.add('s', data); } } class DateTimeContainer { constructor() { pri(this, { time: null }) } SetDateTime(time) { pri(this).__.time = time; } GetDateTime() { return pri(this).__.time; } } /** * 各种Cron标记的基类a,b:a或者b data a/b:a为底b的倍数 data a-b:从a到b data a#b:允许在星期域中出现。这个字符用于指定本月的某某天。例如:“6#3”表示本月第三周的星期五星期日为1 注意这里DayOfWeek 中星期日为0 data aL:在日期和星期意思不同,例如day-of-month域中表示一个月的最后一天。如果在day-of-week域表示周六,如果在day-of-week域中前面加上数字,它表示一个月的最后第几天,例如‘6L’就表示一个月的最后一个星期五 data aW:只允许日期域出现。这个字符用于指定日期的最近工作日。例如:如果你在日期域中写 “15W”,表示:这个月15号最近的工作日 data aC: */ class CronNode { constructor(nodeIdentify, par, dateTime) { pri(this, { //todo 正则待验证 ndeIdentify: new RegExp(nodeIdentify), parent: par, datePart: dateTime }); } get NodeIdentify() { return pri(this).__.ndeIdentify; } Next(container) { const { _, __ } = pri(this); let changeValue = _.partRegen(container.GetDateTime(), __.datePart); if (changeValue != 0) container.SetDateTime(__.datePart.AddTime(container.GetDateTime(), changeValue)); //console.log(__.datePart.name, changeValue + ":" + container.GetDateTime().toString('yyyy MM dd HH mm ss')); //if ((parent != null && parent.Next(container)) || (parent == null && changeValue != 0)) { if ((__.parent != null && __.parent.Next(container) && __.datePart.name != 'DayDateTimePart')) { //特例处理Day和Week //清零 let changeFirst = this.partGetFirst(container.GetDateTime(), __.datePart); //console.log('first ' + __.datePart.name, changeFirst); container.SetDateTime(__.datePart.AddTime(container.GetDateTime(), changeFirst)); return true; } //console.log(__.datePart.name); return changeValue != 0; } } class CommonCronNode extends CronNode { constructor(nodeIdentify, par, dateTime) { super(nodeIdentify, par, dateTime) } partRegen(time, part) { if (part.name == 'DayDateTimePart') return this.DayRegen(part.GetTime(time), part.GetMaxDate(time), part.GetMaxDate(time.add('m', 1))); else return this.Regen(part.GetTime(time), part.GetMaxDate(time)); } partGetFirst(time, part) { if (part.name == 'DayDateTimePart') return this.DayGetFirst(part.GetTime(time), part.GetMaxDate(time), part.GetMaxDate(time.add('m', 1))); else return this.GetFirst(part.GetTime(time), part.GetMaxDate(time)); } /** * 29,30,31号必然可以设置在本月或者下下个月 一般的这里的条件只对2月有用 * @param {*} time * @param {*} maxDate * @param {*} nextMaxDate */ DayRegen(time, maxDate, nextMaxDate) {} /** * 29,30,31号必然可以设置在本月或者下下个月 一般的这里的条件只对2月有用 * @param {*} time * @param {*} maxDate * @param {*} nextMaxDate */ DayGetFirst(time, maxDate, nextMaxDate) {} /** * 仅仅用于处理数字 * @param {*} time * @param {*} maxDate */ Regen(time, maxDate) {} /** * 仅仅用于处理数字 * @param {*} time * @param {*} maxDate */ GetFirst(time, maxDate) {} } /// <summary> /// 处理*号 /// </summary> class XCronNode extends CommonCronNode { constructor(text, par, part) { super("\\*", par, part); } DayRegen(time, maxDate, nextMaxDate) { return 0; } DayGetFirst(time, maxDate, nextMaxDate) { return 1 - time; } Regen(time, maxDate) { return 0; } GetFirst(time, maxDate) { return -1 * time; } } /// <summary> /// 处理?号 /// </summary> class QCronNode extends CronNode { constructor(text, par, part) { super("\\?", par, part); } partRegen(time, part) { return 0; } partGetFirst(time, part) { return 0; } } /// <summary> /// 处理具体数字 /// 请注意星期中1-7需要改为0-6 /// </summary> class NCronNode extends CommonCronNode { constructor(num, par, datePart) { super("\\d+", par, datePart); const { _, __ } = pri(this, { num: 0 }); __.num = parseInt(num); if (datePart.name == 'WeekDateTimePart') __.num--; } Regen(time, maxDate) { const { _, __ } = pri(this); return (time > __.num) ? (maxDate - time + __.num) : (__.num - time); } GetFirst(time, maxDate) { const { _, __ } = pri(this); return __.num - time; } DayRegen(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); //29,30,31号必然可以设置在本月或者下下个月 一般的这里的条件只对2月有用 return this.Regen(time, maxDate) + ((time > __.num && __.num > nextMaxDate) ? nextMaxDate : 0); } DayGetFirst(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (__.num > maxDate) //说明本月无法设置 设置为下个月 return maxDate - time + __.num; return this.GetFirst(time, maxDate); } } /// <summary> /// 处理逗号 /// </summary> class DCronNode extends CommonCronNode { constructor(num, par, datePart) { super("\\d+[,\\d+]+", par, datePart); const { _, __ } = pri(this, { nums: [] }); let _n = num.split(','); for (let w = 0; w < _n.length; w++) if (datePart.name == 'WeekDateTimePart') __.nums[w] = parseInt(_n[w]) - 1; else __.nums[w] = parseInt(_n[w]); __.nums.sort((l, r) => l > r); } GetSmallNum(time) { const { _, __ } = pri(this); if (time <= __.nums[0]) return 0; if (time >= __.nums[__.nums.length - 1]) return __.nums.length - 1; let l = 0, r, m; r = __.nums.length; while (r - l > 1) { m = parseInt((l + r) / 2); if (time >= __.nums[m]) l = m; else r = m; } return l; } Regen(time, maxDate) { const { _, __ } = pri(this); //当前数字已经大于最大的数 if (time > __.nums[__.nums.length - 1]) return maxDate - time + __.nums[0]; //maxDate - time + let order = _.GetSmallNum(time); return (time > __.nums[order]) ? (__.nums[order + 1] - time) : __.nums[order] - time; } GetFirst(time, maxDate) { const { _, __ } = pri(this); return __.nums[0] - time; } DayRegen(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (time > __.nums[__.nums.length - 1]) { //说明下个月也无法设置 设置为下下个月 //29,30,31号必然可以设置在本月或者下下个月 一般的这里的条件只对2月有用 return maxDate - time + __.nums[0] + (__.nums[0] > nextMaxDate ? nextMaxDate : 0); } let order = this.GetSmallNum(time); return (time > __.nums[order]) ? (__.nums[order + 1] - time) : __.nums[order] - time; } DayGetFirst(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (__.nums[0] > maxDate) //说明本月无法设置 设置为下个月 return maxDate - time + __.nums[0]; return this.GetFirst(time, maxDate); } } /// <summary> /// -号 //todo /// </summary> class SCronNode extends CommonCronNode { constructor(num, par, datePart) { super("\\d+-\\d+", par, datePart); const { _, __ } = pri(this, { nums: [] }); const _n = num.split('-'); let l = parseInt(_n[0]); let r = parseInt(_n[1]); for (let w = 0; w < r - l + 1; w++) if (datePart.name == 'WeekDateTimePart') __.nums[w] = w + l - 1; else __.nums[w] = w + l; } GetSmallNum(time) { const { _, __ } = pri(this); if (time <= __.nums[0]) return 0; if (time >= __.nums[__.nums.length - 1]) return __.nums.length - 1; let l = 0, r, m; r = __.nums.length; while (r - l > 1) { m = parseInt((l + r) / 2); if (time >= __.nums[m]) l = m; else r = m; } return l; } Regen(time, maxDate) { const { _, __ } = pri(this); //当前数字已经大于最大的数 if (time > __.nums[__.nums.length - 1]) return maxDate - time + __.nums[0]; let order = _.GetSmallNum(time); return (time > __.nums[order]) ? (__.nums[order + 1] - time) : __.nums[order] - time; } GetFirst(time, maxDate) { const { _, __ } = pri(this); return __.nums[0] - time; } DayRegen(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (time > __.nums[__.nums.length - 1]) { //说明下个月也无法设置 设置为下下个月 //29,30,31号必然可以设置在本月或者下下个月 一般的这里的条件只对2月有用 return maxDate - time + __.nums[0] + (__.nums[0] > nextMaxDate ? nextMaxDate : 0); } let order = _.GetSmallNum(time); //当前数字已经大于最大的数 return (time > __.nums[order]) ? (__.nums[order + 1] - time) : __.nums[order] - time; } DayGetFirst(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (__.nums[0] > maxDate) //说明本月无法设置 设置为下个月 return maxDate - time + __.nums[0]; return _.GetFirst(time, maxDate); } } /// <summary> /// 除号 /// </summary> class PCronNode extends CommonCronNode { constructor(num, par, part) { super("\\d+/\\d+", par, part); const { _, __ } = pri(this); _.l = 0; _.r = 0; let _n = num.split('/'); _.l = parseInt(_n[0]); _.r = parseInt(_n[1]); if (part.name == 'WeekDateTimePart') { _.l--; } } GetBigNum(time) { const { _, __ } = pri(this); return (parseInt((time - _.l) / _.r) + 1) * _.r + _.l; } DayRegen(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (time > _.l && (time - _.l) % _.r == 0) return 0; let value = _.GetBigNum(time); if (value > maxDate) //如果下个月不能设置那么就设置到下下个月 return maxDate - time + _.l + (_.l > nextMaxDate ? nextMaxDate : 0); else return value - time; } DayGetFirst(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (_.l > maxDate) //如果本月设置不了那么下个月肯定可以设置 return maxDate - time + _.l; return _.l - time; } Regen(time, maxDate) { const { _, __ } = pri(this); if (time >= _.l && (time - _.l) % _.r == 0) return 0; let value = _.GetBigNum(time); if (value > maxDate) return maxDate - time + _.l; else return value - time; } GetFirst(time, maxDate) { const { _, __ } = pri(this); return _.l - time; } } /// <summary> /// #号 注意将1-7转为0-6 /// </summary> class ACronNode extends CronNode { constructor(num, par, part) { super("[1-7]#[1-5]", par, part); const { _, __ } = pri(this, { GetMaxDay(time, part) { if (part.name == 'WeekDateTimePart') return new Date(time.getFullYear(), time.getMonth() + 1, 1).add('d', -1).getDate(); else return part.GetMaxDate(time); } }); _.l = 0; _.r = 0; let _n = num.split('#'); _.l = parseInt(_n[0]); _.r = parseInt(_n[1]); } /// <summary> /// 得到第r个星期l是几号 /// </summary> /// <param name="time"></param> /// <param name="weekDay"></param> /// <returns></returns> GetRightDay(time, weekDay) { const { _, __ } = pri(this); //firstDay=7- (time - weekDay-1) % 7; //if (firstDay == 7) // firstDay = 0; //firstDay = Math.Abs((time - weekDay - 1) % 7); const firstDay = ((1 - time + weekDay) % 7 + 7) % 7; return 7 * (this.r - 1) + 1 + _.l - firstDay + (this.l < firstDay ? 7 : 0); } partRegen(time, part) { const { _, __ } = pri(this); let num = _.GetRightDay(time.getDate(), time.getDay()); let maxDate = __.GetMaxDay(time, part); //判断如果正确的时间还未发生 if (time.getDate() <= num && num <= maxDate) { return num - time.getDate(); } else { let value = 0; //判断如果正确的时间已经过期 while (time.getDate() > num || maxDate < num) { //下个月1号 let _t = maxDate - time.getDate() + 1; value += _t; time = time.add('d', _t); num = _.GetRightDay(time.getDate(), time.getDay()); maxDate = __.GetMaxDay(time, part); } return value + num - time.getDate(); } } partGetFirst(time, part) { const { _, __ } = pri(this); let num = _.GetRightDay(time.getDate(), time.getDay()); let maxDate = __.GetMaxDay(time, part); if (time.getDate() <= num && num <= maxDate) { return time.getDate() - num; } else { let value = 0; while (time.getDate() > num || maxDate < num) { //下个月1号 let _t = maxDate - time.getDate() + 1; value += _t; time = time.add('d', _t); num = _.GetRightDay(time.getDate(), time.getDay()); maxDate = __.GetMaxDay(time, part); } return value + num - time.getDate(); } } } /// <summary> /// W号 /// </summary> class WCronNode extends CronNode { constructor(num = '', par, part) { super("(\\d+|L)W", par, part); const { _, __ } = pri(this); _.l = 0; if (num.toUpperCaseCase() == "LW") _.l = 31; else _.l = parseInt(num.substr(0, num.length - 1)); } /// <summary> /// 得到l日附近的工作日是几号 /// </summary> /// <param name="time"></param> /// <param name="weekDay"></param> /// <returns></returns> GetRightDay(time, maxDate, weekDay) { //firstDay = 7 - (time - weekDay - 1) % 7; //if (firstDay == 7) // firstDay = 0; //return ((time-1)%7+firstDay)%7; const { _, __ } = pri(this); let _l = Math.min(_.l, maxDate); let r = ((_l - time + weekDay) % 7 + 7) % 7; if (r > 5) return _l - 1; if (r < 1) return _l + 1; return _l; } partRegen(time, part) { let maxDate = part.GetMaxDate(time); let num = _.GetRightDay(time.getDate(), maxDate, time.getDay()); if (time.getDate() <= num && maxDate >= num) return num - time.getDate(); else { return maxDate - time.getDate() + _.GetRightDay(1, part.GetMaxDate(time.add('m', 1)), ((1 + maxDate - time.getDate() + time.getDay()) % 7 + 7) % 7); } } partGetFirst(time, part) { return this.GetRightDay(time.getDate(), part.GetMaxDate(time), time.getDay()) - time.getDate(); } } /// <summary> /// 处理最后几天,或者最后一个星期几的问题 /// </summary> class LCronNode extends CronNode { constructor(num, par, part) { super("\\d*L", par, part); const { _, __ } = pri(this, { GetMaxDay: function(time, part) { if (part.name == 'WeekDateTimePart') return new Date(time.getFullYear(), time.getMonth() + 1, 1).add('d', -1).getDate(); else return part.GetMaxDate(time); } }); _.l = 0; if (num.length > 1) _.l = parseInt(num.substr(0, num.length - 1)); if (part.name == 'WeekDateTimePart' && _.l > 0) { _.l--; } } /// <summary> /// 得到l日附近的工作日是几号 /// </summary> /// <param name="time"></param> /// <param name="weekDay"></param> /// <returns></returns> GetRightDay(time, part) { const { _, __ } = pri(this); if (part.name == 'WeekDateTimePart') { let last = __.GetMaxDay(time, part); //得到最后一天是星期几 let lastDay = ((last - time.getDate() + time.getDay()) % 7 + 7) % 7; return last + _.l - lastDay - (_.l < lastDay ? 0 : 7); } else return part.GetMaxDate(time) - _.l; } partRegen(time, part) { const { _, __ } = pri(this); let maxDate = __.GetMaxDay(time, part); let num = _.GetRightDay(time, part); if (time.getDate() <= num && maxDate >= num) return num - time.getDate(); else return maxDate - time.getDate() + _.GetRightDay(time.add('m', 1), part); } partGetFirst(time, part) { const { _, __ } = pri(this); let maxDate = __.GetMaxDay(time, part); let num = _.GetRightDay(time, part); if (time.getDate() <= num && maxDate >= num) return time.getDate() - num; else return maxDate - time.getDate() + _.GetRightDay(time.add('m', 1), part); } } /// <summary> /// 处理几号以后 或者星期几以后 /// </summary> class CCronNode extends CommonCronNode { constructor(num, par, part) { super("\\d+C", par, part); const { _, __ } = pri(this); _.l = 0; if (num.length > 1) _.l = parseInt(num.substr(0, num.length - 1)); if (part.name == 'WeekDateTimePart') { _.l--; } } DayRegen(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); if (time >= _.l) return 0; else return _.l - time + ((_.l > maxDate) ? maxDate : 0); } DayGetFirst(time, maxDate, nextMaxDate) { const { _, __ } = pri(this); return _.l - time; } Regen(time, maxDate) { const { _, __ } = pri(this); if (time >= _.l) return 0; else return _.l - time; } GetFirst(time, maxDate) { const { _, __ } = pri(this); return _.l - time; } } const RegExpS = [ new RegExp(V.format("(^\\*$)|(^{data}([-/]{data})?$)|(^{data}(,{data})+$)", { data: "[1-5]?[0-9]" }), 'i'), new RegExp(V.format("(^\\*$)|(^{data}([-/]{data})?$)|(^{data}(,{data})+$)", { data: "[1-5]?[0-9]" }), 'i'), new RegExp(V.format("(^\\*$)|(^{data}([-/]{data})?$)|(^{data}(,{data})+$)", { data: "[1-2]?[0-9]" }), 'i'), new RegExp(V.format("(^[\\*\\?]$)|(^{data}([-/]{data})?$)|(^{data}?[LWC]$)|(^{data}(,{data})+$)|(^LW$)", { data: "[1-3]?[0-9]" }), 'i'), new RegExp(V.format("(^\\*$)|(^{data}([-/]{data})?$)|(^{data}(,{data})+$)", { data: "1?[0-9]" }), 'i'), new RegExp(V.format("(^[\\*\\?]$)|(^{data}([-/#]{data})?$)|(^{data}?[LC]$)|(^{data}(,{data})+$)", { data: "[1-7]" }), 'i'), new RegExp(V.format("(^\\*$)|(^{data}([-/]{data})?$)|(^{data}(,{data})+$)", { data: "[0-9]{4}" }), 'i') ]; const FIELDLIMIT = [ [0, 59], [0, 59], [0, 23], [1, 31], [1, 12], [1, 7], [1, 9999] ]; const PARTS = [new SecondDateTimePart(), new MinuteDateTimePart(), new HourDateTimePart(), new DayDateTimePart(), new WeekDateTimePart(), new MonthDateTimePart(), new YearDateTimePart()]; const TYPES = [XCronNode, QCronNode, NCronNode, DCronNode, SCronNode, PCronNode, ACronNode, WCronNode, LCronNode, CCronNode]; const CRONRegExp = [new RegExp("^\\*$", 'gi'), new RegExp("^\\?$", 'gi'), new RegExp("^\\d+$", 'gi'), new RegExp("^\\d+[,\\d+]+$", 'gi'), new RegExp("^\\d+-\\d+$", 'gi'), new RegExp("^\\d+/\\d+$", 'gi'), new RegExp("^[1-7]#[1-5]$", 'gi'), new RegExp("^(\\d+|L)W$", 'gi'), new RegExp("^\\d*L$", 'gi'), new RegExp("^\\d+C$", 'gi')]; const CreateCronNode = function(text, node, part) { for (let w = 0; w < CRONRegExp.length; w++) { CRONRegExp[w].lastIndex = 0; //每次调用test回调指针 if (CRONRegExp[w].test(text) ? true : false) return V.create2(TYPES[w], [text, node, part]); } throw new Error(text + "没有找到合适的表示式元素!"); } const NUMRegExp = new RegExp("\\d+", 'g'); const MatchCronExpression = function(text) { for (let w = 0; w < 7; w++) { if (!RegExpS[w].test(text[w])) throw new Error(V.format("第{id}项不符合要求:{desc}", { id: w + 1, desc: text[w] })); const matchs = text[w].match(NUMRegExp) || []; for (let i = 0; i < matchs.length; i++) { const num = parseInt(matchs[i]); if (!(FIELDLIMIT[w][0] <= num & FIELDLIMIT[w][1] >= num)) throw new Error(V.format("第{id}项超出范围:{desc}", { id: w + 1, desc: text[w] })); } } return true; } /** * 使用require('cron-parser')进行克隆表达式封装 * @param {*} 克隆表达式 * @param {*} 当前时间 */ export const Cron = class { constructor(expression) { const { _, __ } = pri(this, { nodes: null }); expression = expression.trim(); if (expression.split(' ').length < 7) expression += " *"; let exp = expression.toUpperCase().split(' '); MatchCronExpression(exp); //替换月与星期的位置 理顺嵌套关系! const _t = exp[5]; exp[5] = exp[4]; exp[4] = _t; for (let w = 6; w >= 0; w--) { __.nodes = CreateCronNode(exp[w], __.nodes, PARTS[w]); } } /* *(^\*$)|(^[1-5]?[0-9]([-/][1-5]?[0-9])?$)|(^[1-5]?[0-9](,[1-5]?[0-9])+$) (^\*$)|(^[1-5]?[0-9]([-/][1-5]?[0-9])?$)|(^[1-5]?[0-9](,[1-5]?[0-9])+$) (^\*$)|(^[1-2]?[0-9]([-/][1-2]?[0-9])?$)|(^[1-2]?[0-9](,[1-2]?[0-9])+$) (^[\*\?]$)|(^[1-3]?[0-9]([-/][1-3]?[0-9])?$)|(^[1-3]?[0-9]?[LWC]$)|(^[1-3]?[0-9](,[1-3]?[0-9])+$) (^\*$)|(^1?[0-9]([-/]1?[0-9])?$)|(^1?[0-9](,1?[0-9])+$) (^[\*\?]$)|(^[1-7]([-/#][1-7])?$)|(^[1-7]?[LC]$)|(^[1-7](,[1-7])+$) (^\*$)|(^[0-9]{4}([-/][0-9]{4})?$)|(^[0-9]{4}(,[0-9]{4})+$) FieldName = new String[] { "秒", "分", "小时", "日期", "月", "星期", "年" }; */ next(time = new Date()) { const { _, __ } = pri(this); const container = new DateTimeContainer(); container.SetDateTime(time.add('s', 1)); while (__.nodes.Next(container)); return container.GetDateTime(); } } export default { Cron }; const pri = V.pris();