时间表 2.1.0

时间表 2.1.0

jianstm 维护。



时间表 2.1.0

  • 作者:
  • Quentin Jin

Schedule(简体中文)

Schedule 是一个用 Swift 编写的定时任务调度器。它允许您以优雅直观的语法运行定时任务。

特性

  • 优雅直观的 API
  • 丰富的预设规则
  • 强大的管理机制
  • 详细的执行历史记录
  • 线程安全
  • 完善的文档
  • ~100%+ 的测试覆盖率

为什么你应该使用 Schedule

特性 计时器 DispatchSourceTimer 时间表
基于间隔的时间表
📆 基于日期的时间表
🌈组合计划时间表
🗣️自然语言解析
🏷批处理任务管理
📝执行记录
🎡计划重置
🚦暂停,恢复,取消
🍰子操作

使用方法

概述

任务排期从未如此优雅且直观,您只需

// 1. define your plan:
let plan = Plan.after(3.seconds)

// 2. do your task:
let task = plan.do {
    print("3 seconds passed!")
}

规则

基于间隔的排期

排期的运行机制基于 Plan,而实际上 Plan 是一系列 Interval

通过扩展 IntDouble,排期使得 Plan 定义更加优雅和直观。此外,因为 Interval 是排期的内置类型,您不必担心它污染您的命名空间。

let t1 = Plan.every(1.second).do { }

let t2 = Plan.after(1.hour, repeating: 1.minute).do { }

let t3 = Plan.of(1.second, 2.minutes, 3.hours).do { }

基于日期的排期

配置基于日期的 Plan 与此相同,使用表达性强的 Swift 语法,排期使您的代码看起来像是一场流畅的对话。

let t1 = Plan.at(date).do { }

let t2 = Plan.every(.monday, .tuesday).at("9:00:00").do { }

let t3 = Plan.every(.september(30)).at(10, 30).do { }

let t4 = Plan.every("one month and ten days").do { }

let t5 = Plan.of(date0, date1, date2).do { }

自然语言解析

除了这个,排期还支持简单的自然语言解析。

let t1 = Plan.every("one hour and ten minutes").do { }

let t2 = Plan.every("1 hour, 5 minutes and 10 seconds").do { }

let t3 = Plan.every(.friday).at("9:00 pm").do { }

Period.registerQuantifier("many", for: 100 * 1000)
let t4 = Plan.every("many days").do { }

组合排期

排期提供了一些基本的集合运算符,这意味着您可以使用它们来自定义您自己的强大计划。

/// Concat
let p0 = Plan.at(birthdate)
let p1 = Plan.every(1.year)
let birthday = p0.concat.p1
let t1 = birthday.do { 
    print("Happy birthday")
}

/// Merge
let p3 = Plan.every(.january(1)).at("8:00")
let p4 = Plan.every(.october(1)).at("9:00 AM")
let holiday = p3.merge(p4)
let t2 = holiday.do {
    print("Happy holiday")
}

/// First
let p5 = Plan.after(5.seconds).concat(Schedule.every(1.day))
let p6 = s5.first(10)

/// Until
let p7 = P.every(.monday).at(11, 12)
let p8 = p7.until(date)

管理

DispatchQueue

调用 plan.do 来调度定时任务时,您可以使用 queue 指定任务在时间到达时将被调度到哪个 DispatchQueue。这个操作不依赖于 RunLoop,就像 Timer 一样,因此您可以在任何线程上调用它。

Plan.every(1.second).do(queue: .global()) {
    print("On a globle queue")
}

RunLoop

如果没有指定 queue,调度程序将使用 RunLoop 来调度任务,此时任务将在当前线程上执行。请注意,就像也基于 RunLoopTimer 一样,您需要确保当前线程有一个**可用**的 RunLoop。默认情况下,任务将被添加到 .common 模式,您可以在创建任务时指定另一个模式。

let task = Plan.every(1.second).do(mode: .default) {
    print("on default mode...")
}

时间线

您可以使用以下属性实时观察任务的执行记录。

task.creationDate

task.executionHistory

task.firstExecutionDate
task.lastExecutionDate

task.estimatedNextExecutionDate

任务中心 & 标签

默认情况下,任务将自动添加到 TaskCenter.default,您可以使用标签和任务中心来组织它们。

let plan = Plan.every(1.day)
let task0 = plan.do(queue: myTaskQueue) { }
let task1 = plan.do(queue: myTaskQueue) { }

TaskCenter.default.addTags(["database", "log"], to: task1)
TaskCenter.default.removeTag("log", from: task1)

TaskCenter.default.suspend(byTag: "log")
TaskCenter.default.resume(byTag: "log")
TaskCenter.default.cancel(byTag: "log")

TaskCenter.default.clear()

let myCenter = TaskCenter()
myCenter.add(task0)

挂起,暂停,取消

您可以挂起、暂停、取消一个任务。

let task = Plan.every(1.minute).do { }

// will increase task's suspensionCount
task.suspend()

// will decrease task's suspensionCount,
// but don't worry about excessive resumptions, I will handle these for you~
task.resume()

// will clear task's suspensionCount
// a canceled task can't do anything, event if it is set to a new plan.
task.cancel()

操作

您可以随时向任务添加更多操作并移除它们

let dailyTask = Plan.every(1.day)
dailyTask.addAction {
    print("open eyes")
}
dailyTask.addAction {
    print("get up")
}
let key = dailyTask.addAction {
    print("take a shower")
}
dailyTask.removeAction(byKey: key)

安装

CocoaPods

# Podfile
use_frameworks!

target 'YOUR_TARGET_NAME' do
  pod 'Schedule', '~> 2.0'
end

Carthage

github "luoxiu/Schedule" ~> 2.0

Swift包管理器

dependencies: [
    .package(
      url: "https://github.com/luoxiu/Schedule", .upToNextMajor(from: "2.0.0")
    )
]

贡献

喜欢时间表吗?谢谢!!

同时,我需要您的帮助~

发现错误

时间表刚刚开始。如果您能帮助时间表查找或修复潜在的错误,我将不胜感激!

新特性

有一些很棒的想法吗?请随时提出问题或直接提交您的 pull 请求!

文档改进。

对 README 和文档的改进是非常受欢迎的,无论是错别字还是蹩脚的英语。🤣.

致谢

灵感来源于 Dan Bader 的 schedule!