目录
1、使用场景
最近项目有个一个需求实现,查询某月的日历相关的事件信息,里面包含有一门课程的开始时间和结束时间,以及自定义相关日历提示信息。在点击某个日历天之后显示某一天的事件详情。
2、业务逻辑实现
数据来源有两部分。
第1部分: 分派给学员的课程有开始时间和结束时间,因为前期业务处理可能开始或者结束时间有为0(标识未设置),也有两者都设置的。于是查询在日历之中查询需要获得选中月份的第一天 00:00:00:000 和最后一天的 23:59:59:999。
第2部分:用户自定义发送的日历信息。
另外在点击日历某个日期的时候,需要显示某一天的详情,此时需要显示某天内的
00:00:00:000 到某一天结束 23:59:59:999。
于是需要计算给定时间戳的,所在月的开始第一天和最后一天;以及指定的某天 的开始和结束时间戳。
注意事项:我们查询的时候可能查询的 开始时间和结束时间落到指定区间内容;但是会出现一种情况,开始时间在要求的某天或者某月;但是结束时间在另外一天或者一月;此时虽然要求把开始和结束时间的一条记录拆分未两条记录;但是需要通过时间戳进行过滤掉不在指定范围内容(某天/某月)记录。
boolean conditionEnd = (null != endTime && (beginTime >= monthFirstDayTime && beginTime < monthFirstEndTime));
3、实现代码展示
<!-- 查询学生课程日历数据通过学员所在所有班级的课程开课和结课 -->
<select id="selectStudentCourseCalendarListByClazzIds" resultMap="studentCalenderCourseDTO">
select
occ.id,
occ.course_id,
occ.clazz_id,
c.name as day_title,
occ.begin_time,
occ.end_time,
0 as program_id,
'' as color,
'' as event_content
from (
select t.id,
t.course_id,
t.clazz_id,
unix_timestamp(cast(FROM_UNIXTIME(t.begin_time/1000,'%Y-%m-%d') as date))*1000 begin_time,
unix_timestamp(cast(FROM_UNIXTIME(t.end_time/1000,'%Y-%m-%d') as date))*1000 end_time
from l_clazz_course t
where t.delete_time = 0
and (t.begin_time!=0 or t.end_time!=0)
and (
<!-- 开始时间 在指定月份之间 -->
(t.begin_time >= #{monthFirstDayTime} and t.begin_time < #{monthFirstEndTime})
<!-- 结束时间 在指定月份之间 -->
or (t.end_time >= #{monthFirstDayTime} and t.end_time < #{monthFirstEndTime})
)
<if test="clazzIdList!=null">
and t.clazz_id in
<foreach collection="clazzIdList" index="index" item="id" separator="," open="(" close=")">
#{id,jdbcType=BIGINT}
</foreach>
</if>
) occ
left join l_course c on
occ.course_id = c.id
</select>
/**
* 处理课程之中有开始和结束时间数据
*
* @param studentCalendarDtoList
* @param calenderCourseDTO
* @param monthFirstDayTime
* @param monthFirstEndTime
* @param isAddPrefixFlag
*/
private void dealCalendarBeginAndEndTime(List<StudentCalendarDTO> studentCalendarDtoList, StudentCalenderCourseDTO calenderCourseDTO,
Long monthFirstDayTime, Long monthFirstEndTime,
boolean isAddPrefixFlag) {
String calenderDayTitle = calenderCourseDTO.getCalenderDayTitle();
Long courseId = calenderCourseDTO.getCourseId();
Long clazzCourseId = calenderCourseDTO.getClazzCourseId();
//获得开始时间 日历信息
Long beginTime = calenderCourseDTO.getBeginTime();
boolean conditionBegin = (null != beginTime && (beginTime >= monthFirstDayTime && beginTime < monthFirstEndTime));
if (conditionBegin) {
StudentCalendarDTO studentCalendarDtoBegin = new StudentCalendarDTO();
studentCalendarDtoBegin.setEventCalendarTime(beginTime);
studentCalendarDtoBegin.setClazzCourseId(clazzCourseId);
studentCalendarDtoBegin.setCourseId(courseId);
if (isAddPrefixFlag) {
String startCourse = MessageUtils.message("studentIndex.calendar.course.start");
studentCalendarDtoBegin.setEventShortTitle(startCourse + calenderDayTitle);
} else {
studentCalendarDtoBegin.setEventShortTitle(calenderDayTitle);
}
studentCalendarDtoBegin.setColor(BusinessConstants.STUDENT_CALENDAR_COURSE_BEGIN_COLOR);
studentCalendarDtoList.add(studentCalendarDtoBegin);
}
//获得结束时间 日历信息
Long endTime = calenderCourseDTO.getEndTime();
boolean conditionEnd = (null != endTime && (beginTime >= monthFirstDayTime && beginTime < monthFirstEndTime));
if (conditionEnd) {
StudentCalendarDTO studentCalendarDtoEnd = new StudentCalendarDTO();
studentCalendarDtoEnd.setEventCalendarTime(endTime);
studentCalendarDtoEnd.setClazzCourseId(clazzCourseId);
studentCalendarDtoEnd.setCourseId(courseId);
if (isAddPrefixFlag) {
String endCourse = MessageUtils.message("studentIndex.calendar.course.end");
studentCalendarDtoEnd.setEventShortTitle(endCourse + calenderDayTitle);
} else {
studentCalendarDtoEnd.setEventShortTitle(calenderDayTitle);
}
studentCalendarDtoEnd.setColor(BusinessConstants.STUDENT_CALENDAR_COURSE_END_COLOR);
studentCalendarDtoList.add(studentCalendarDtoEnd);
}
}
通过时间戳 获得某月的第一天和最后一天,某天的开始和结束时间(DateUtil为hutool工具类)
/**
* 根据时间戳获得当前月份第一天
*
* @param dataTimeStamp
* @return
*/
public Long getMonthFirstDayTime(Long dataTimeStamp) {
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(dataTimeStamp);
calendar.set(Calendar.DAY_OF_MONTH, 1);
calendar.add(Calendar.MONTH, 0);
calendar.getTimeInMillis();
String firstDay = DateUtil.format(calendar.getTime(), "yyyy-MM-dd");
Date firstDate = DateUtil.parse(firstDay);
Long milliSecond = firstDate.getTime();
return milliSecond;
}
/**
* 根据时间戳获得当前月份最后天
*
* @param dataTimeStamp
* @return
*/
public Long getMonthLastDayTime(Long dataTimeStamp) {
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(dataTimeStamp);
calendar.set(Calendar.DAY_OF_MONTH, calendar.getActualMaximum(Calendar.DAY_OF_MONTH));
String lastDay = DateUtil.format(calendar.getTime(), "yyyy-MM-dd");
Date lastDate = DateUtil.parse(lastDay);
Long milliSecond = lastDate.getTime() + BusinessConstants.HOUR24_MILLISECOND;
return milliSecond;
}
/**
* 根据时间戳获得当天 00:00:00
*
* @param dataTimeStamp
* @return
*/
public Long getSomeDayStartTime(Long dataTimeStamp) {
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(dataTimeStamp);
calendar.set(Calendar.HOUR, 0);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MILLISECOND, 0);
calendar.getTimeInMillis();
Long milliSecond = calendar.getTimeInMillis();
return milliSecond;
}
/**
* 根据时间戳获得当天 23:59:59
*
* @param dataTimeStamp
* @return
*/
public Long getSomeDayEndTime(Long dataTimeStamp) {
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(dataTimeStamp);
calendar.set(Calendar.HOUR, 23);
calendar.set(Calendar.MINUTE, 59);
calendar.set(Calendar.SECOND, 59);
calendar.set(Calendar.MILLISECOND, 999);
Long milliSecond = calendar.getTimeInMillis();
return milliSecond;
}
4、成果展现
4、总结
我们日常工作之中可能会经常使用到,查询某月或者某天 开始和结束时间。此实现方法应该用得比较多,记录一下以备后面需要。另外可能Hutools有类似实现方法就更加简单。