Skip to content

概念

时间模式是指时间的安排,如周一到周五的工作时段,节假日的日期安排。每个时间模式代表了一段时间内的具体工作时间。

时间模式包括两个部分

  • 通常的周几的时间段
    • 如周一,周二,等
  • 特殊日期
    • 如节假日等

时间模式的规则是首先判断特殊日期,如果不是在特殊日期,则用周几的时间段去判断。

每个时段用以下struct表示.

ts
/**
 * 时段(场次)
 */
export interface ITimeSegment {
  /**
   * 'AM', 'PM', or name of time slots
   */
  name: string
  /**
   * Use string to represent time, e.g., "09:00:00"
   */
  start: string
  /**
   * Use string to represent time, e.g., "17:00:00"
   */
  end: string
}

所有时段的时间string都用"HH:MM:SS"的格式。通常精确到分钟,所以SS都是00

这样,每天的时间安排可以用如下结构:

ts
/**
 * 每天的时间段
 */
export interface ITimeModeDay {
  /**
   * 是否全天不开放。如果是true,segments应为空或null
   */
  all_day_closed: boolean
  /**
   * 时段数组。只有all_day_closed为false的时候才有效。
   */
  segments?: ITimeSegment[]
}

时间模式用以下结构表示:

ts
/**
 * 每星期的时间安排
 */
export interface ITimeModeWeekdays {
  mon: ITimeModeDay
  tue: ITimeModeDay
  wed: ITimeModeDay
  thu: ITimeModeDay
  fri: ITimeModeDay
  sat: ITimeModeDay
  sun: ITimeModeDay
}

/**
 * 特殊日期的时间安排
 */
export interface ITimeModeDateOverride {
  /**
   * 名称,例如'国庆节'
   */
  name: string
  /**
   * 日期,格式为 "YYYY-MM-DD"
   */
  date: string
  /**
   * 该天的日期安排
   */
  mode: ITimeModeDay
}

/**
 * 代表时间模式
 */
export interface ITimeModeEntity {
  /**
   * 通常周几的时间安排
   */
  weekdays: ITimeModeWeekdays
  /**
   * 特殊日期的时间安排
   */
  date_overrides: ITimeModeDateOverride[]
}

初始化时间模式

在分店创建时,我们默认创建两种时间模式

  1. 全天24小时,不包括节假日
  2. 早九晚五,不包括周末,节假日按分店国家创建
ts
const holidays = await prisma.holiday.findMany({
  where:  {
    location_id: locationId
  }
})
const dateOverrides = holidays.map((holiday) => {
  date: holiday.format('YYYY-MM-DD'),
  name: holiday.name,
  mode: {
    all_day_closed: true,
    segments: []
  }
})

const timeMode = {
  weekdays: DEFAULT_WORKING_HOUR,
  date_overrides: dateOverrides
}

使用时间模式计算日期

BusinessTimeManager提供了对工作日的计算方式,包括:

isOpenDay - 判断是否当天开放
isCloseDay - 判断是否当天关闭
nextBusinessDay - 下一个工作日
previousBusinessDay - 上一个工作日
...

根据时间模式创建BusinessTimeManager:

ts
timeModeEntity = {
  weekdays: DEFAULT_WORKING_HOURS,
  date_overrides: [],
}
businessTimeManager = new BusinessTimeManager(timeModeEntity)

使用BusinessTimeManager:

ts
businessTimeManager = new BusinessTimeManager(timeModeEntity)
const date = dayjs('2024-12-25')
businessTimeManager.isCloseDay(date)

API

后端提供时间模式API包括:

  1. 获取所有时间模式

GET /api/v5/time_modes

  1. 创建时间模式

POST /api/v5/time_modes

  1. 修改时间模式

PATCH /api/v5/time_modes

  1. 删除时间模式

DELETE /api/v5/time_modes

  1. 获取时间模式详情

GET /api/v5/time_modes/{id}

注意:时间模式的参数为TimeModeWeekdaysTimeModeDateOverride[]的Json格式。所以创建和修改时,需要在原来的时间模式的基础上更新后再传全部struct。

例如:

  1. 增加特殊日期:
    1. 获取时间模式
    2. 在时间模式的date_overrides数组中添加新的TimeModeDateOverride
    3. 调用PATCH方法更新后端
  2. 拷贝时间模式
    1. 获取时间模式
    2. 将原时间模式的数组deep clone
    3. 调用POST方法创建新时间模式

详情显示

使用timeModeAsString(timeMode)函数显示时间模式详情,

'Sun: Closed; Mon: 09:00 - 12:00, 12:00 - 17:00; Tue: 09:00 - 12:00, 12:00 - 17:00; Wed: 09:00 - 12:00, 12:00 - 17:00; Thu: 09:00 - 12:00, 12:00 - 17:00; Fri: 09:00 - 12:00, 12:00 - 17:00; Sat: Closed'

Last updated: