我正在尝试制作一个复杂的查询。我有9周的课程。我试图根据这九周的日期触发一封电子邮件。所以课程就像......
jf892iejf929j
{name: Course Name,
month1: date,
month2: date,
month3: date
}
现在,如果其中一个月的日期是,今天我想说,我想发送一封电子邮件。这就是我现在所拥有的。
const ia = _(courses)
.map((course, id) => ({id, ...course}))
.filter(course => course.course === 'Course Name')
.filter(course => moment(new Date(course.month9)).isSameOrAfter(moment(new Date())))
.map(course => {
if (moment(new Date(course.month1)).isSame(moment(new Date()))) {
HERE IS WHERE I'M TRYING TO AVOID 9 IF THENS
}
})
.value()
我正试着像
那样得到回报 {courseId: courseId,
coursetype: Course,
month: month1 (the original key,
date: date (original value of month1 key
}
我希望这是有道理的......有没有更简单的方法找到与日期相匹配的月份然后交回数据?
所以,我在这里找到了一位当地的导师来指导我,这就是我们所做的。
我们返回了值
,而不是在lodash查询中迭代 const ia = _(courses)
.map((course, id) => ({id, ...course}))
.filter(course => course.course === 'Course Name')
.filter(course => moment(new Date(course.month9)).tz("America/Phoenix").isSameOrAfter(moment(new Date(), 'day').tz("America/Phoenix")))
.value()
然后,我们创建了这样的最终对象:
var finalObj = [];
for (var i = 0; i<ia.length; i++) {
for (var key in ia[i]) {
if (key.indexOf("month") >= 0) {
if (moment(new Date(ia[i [key])).tz("America/Phoenix").isSame(moment(new Date('Mon Jul 10 2017 20:00:00 GMT-0700 (MST)'), 'day').tz("America/Phoenix"))) {
finalObj.push({
"courseId": ia[i].id,
"courseName": ia[i].course,
"month": key,
"date": ia[i][key]
});
}
}
}
}
这确实达到了我想要的效果,但我想知道ES6和Lodash是否有办法达到同样的效果。
答案 0 :(得分:0)
这是一个非常有趣的问题 - 我经常看到的一些问题经常出现,但并不常见。如果您正在使用公共API,则几乎不可能在后端更改它。
从我所看到的,不,没有“正确”的方式这样做,但为了测试(并保持未来开发者的理智)我会鼓励分解更多。
例如,请在此处获取最终摘要:
const ia = _(courses)
.map((course, id) => ({id, ...course}))
.filter(course => course.course === 'Course Name')
.filter(course => moment(new Date(course.month9)).tz("America/Phoenix").isSameOrAfter(moment(new Date(), 'day').tz("America/Phoenix")))
.value()
那太好了,看起来很光滑,因为你有一堆一个衬垫,但是稍后再访问它,呃,不是那么多。
您可以执行以下操作:
// -- BusinessRules.js --
/**
* Does x, y, z check
*/
export const createCourse = (course, id) => ({id, ...course});
/**
* Does x, y, z check
*/
export const isCourseX = course => course.course === 'Course Name';
/**
* Does x, y, z check
*/
function isTimezone(course, timezone) {
return moment(new Date(course.month9))
.tz(timezone)
.isSameOrAfter(
moment(new Date(), 'day').tz(timezone)
);
}
// Use some partial magic to create expressive verbs
export const isTimeZoneArizona = _.partial(isTimezone, "America/Phoenix");
export const isTimeZoneMelbourne = _.partial(isTimezone, "Aussie/Melbourne");
// -- App.js --
const ia = _(courses)
.map(createCourse)
.filter(isCourseX)
.filter(isTimeZoneArizona)
.value();
它看起来与您的相似,但您现在可以构建一整套业务规则,尽可能复杂,而不会“混淆”主流。
它也更容易测试,因为您可以轻松地单独测试每个“规则”。
您还可以根据需要轻松添加更多规则。一旦经过测试,规则也可以与其他过滤器序列共享。
修改强> 作为旁注,避免链条,他们可以回来困扰你 - 而且他们要求你拉入所有的lodash来使用它们。
使用上面介绍的精确方法,您可以使用以下内容简化它:
const a = courses.map(createCourse).filter(isCourseX).filter(isTimeZoneArizone);