vapor/queues

Schedule job every x minutes

khoogheem opened this issue ยท 6 comments

Looks like there is no way to make ScheduledJobs run every X hours or X Mins.

The current helpers if I am not mistaken are every 1 min, 1 hour..

I don't see a way to create a ScheduledBuilder and use that to schedule a job.

looks like the jobs.schedule() calls the mutating function self.storage.configuration.schedule(job, builder: builder) which is internal.

ok.. so I kinda found that this works. for doing something every 10 mins.. but surely we can come up with something easier:

    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 0))
    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 10))
    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 20))
    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 30))
    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 40))
    app.jobs.schedule(ApiPerformanceJob(app)).hourly().at(ScheduleBuilder.Minute(integerLiteral: 50))

I don't think this is supported yet. Maybe this would be a good API:

app.jobs.schedule(SomeJob()).minutely().every(10)

@tanner0101 That looks like it would make sense.. everything I was thinking about the other day.. just didn't convey what it should do.

My temporary approach for running a job every 5 minutes:

struct MyJob : ScheduledJob {
  // start with 4 to ensure first run happens immediately
  static var inter: Int = 4

  func run(c: QueueContext) -> EventLoopFuture<Void> {
    // internal counter increments by one, modulo 5 (so wraps to 0 every five minutes)
    MyJob = (MyJob + 1) % 5
    if MyJob > 0 {
      return context.eventLoop.future()
    }
    // 
    // --- do actual work --
    ...
  }
}

๐Ÿ‘

Would be cool if the schedule builder was public as well so you can implement your own, e.g.:

app.jobs.schedule(SomeJob()).custom(SolarNoonScheduler(lat: 78.651, long: 376.990))

Issue seems to be quiet but I too would love this functionality, my workaround is very much similar to Kevin's. Though I've made it a little more flexible in an extension ๐Ÿ˜„

extension Application.Queues {
    func scheduleEvery(_ job: ScheduledJob, minutes: Int) {
        for minuteOffset in stride(from: 0, to: 60, by: minutes) {
            schedule(job).hourly().at(.init(integerLiteral: minuteOffset))
        }
    }
}