Git Product home page Git Product logo

job_scheduler's People

Contributors

apollo13 avatar jordanmack avatar lholden avatar lisqorz avatar mjanda avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar

job_scheduler's Issues

Day of Week, expression "1-5" results in execution on Sunday?

Hi,

I use the expression "1-5" for weekdays for a job running at 1pm.
After I schedule, when I check on Friday after the execution with time_till_next_job and calculate, I get an execution on Sunday!

For cron, the values "0" and "7" designate sundays.

Is there a bug with array start or something? Can you verify this on your side?

Best Regards,
Thomas

Ability to remove job from schedule

Please add the ability to remove a job from the schedule.
JobScheduler::add() could return a JobId and then a job can be removed via its JobId.

Add timezone configuration

Hi ! Since, Schedule support timezones, it would be useful to configure JobScheduler with a custom timezone, such as chrono::offset::Local.

Please update cron

the cron lib you are using '0.2.0' has some problems with the most recent version of rust. can you update to the newer version?

Meet a issue when I add the notification handler to Job

When I create a new Job for shared Scheduler, the job could not add notication handler.

let mut jobsch = get_scheduler().clone();
jobsch.shutdown().await?;
let job = Job::new_repeated_async(Duration::from_millis(100u64), run)?;
// job.on_done_notification_add(&jobsch, async move |_, _, |{});
log::info!("Do add a job notification {}", jobsch.inited.read().await);
// below code will locked this thread
match job.on_notifications_add(&jobsch, Box::new(|job_id, notification_id, type_of_notification| {
Box::pin(async move {
println!("Job {:?} was completed, notification {:?} ran ({:?})", job_id, notification_id, type_of_notification);
})
}), vec![tokio_cron_scheduler::JobNotification::Done]).await {
Ok(
) => {},
Err(err) => {
log::info!("add notic failed {}", err);
},
}
log::info!("Do add a job into scheduler"); // this code will not be reached.
get_scheduler().add(job).await

* 0/2 * * * * * every two minutes seems to run every second

I can't seem to get a task to run every two minutes. What am I doing wrong ?

Thanks

extern crate chrono;
extern crate crossbeam;
extern crate liblasso;

use std::time::Duration;
use liblasso::job_scheduler::;
use std::{thread, time};
use chrono::
;

#[test]
fn schedule_simple() {

let mut sched = JobScheduler::new();

sched.add(Job::new("* 0/2 * * * * *".parse().unwrap(), move || {
    println!("{}: Hello World (every 2 minutes)!", Utc::now());
}));

loop {
    sched.tick();
    //sched.tick_async();

    std::thread::sleep(Duration::from_millis(500));
}

}

`dyn std::ops::FnMut()` cannot be sent between threads safely

Thanks for this crate. It'd be handy to use it in async programs.

run: Box<dyn (FnMut() -> ()) + 'a> causes

`dyn std::ops::FnMut()` cannot be sent between threads safely

in the following example:

use job_scheduler::{Job, JobScheduler};
use std::time::Duration;
use tokio::time::delay_for;

#[tokio::main]
async fn main() {
    let mut scheduler = JobScheduler::new();
    scheduler.add(Job::new("1/1 * * * * * *".parse().unwrap(), || {
        dbg!("hello");
    }));
    tokio::spawn(async move {
        loop {
            scheduler.tick();
            delay_for(Duration::from_millis(500)).await;
        }
    })
    .await
    .unwrap();
}
[package]
name = "hello_job_scheduler"
version = "0.1.0"
edition = "2018"

[dependencies]
job_scheduler = "1"
tokio = { version = "0.2", features = ["rt-threaded", "macros", "time"]}

When one job takes long, it causes other jobs to run multiple times afterwards (in same tick() call), violating their interval time

When I have several jobs that run in certain intervals, when one job takes a long time, the same tick() call that is running this job will run the jobs that would have run in the meantime, and it will also run the jobs multiple times if they would have run multiple times in the meantime (in that same tick() call).
I'd prefer if the tick() call would only execute one pending job AND if jobs that should have run in the past were debounced so that they run at most 1 times, and only on the next tick() call.

It would also be more intuitive if each tick() call only ran 1 job at most..

In my use case, I have one job that checks for an update of the client regularly, and when an update is available, it downloads it, extracts the executable from the zip, overwrites the current executable and then sets a flag that is used by the outer while loop to terminate. So after a successful update, the executable should break out of the loop (and it is then restarted automatically (because it's a systemd service with Restart=always)), but because of the current behavior of tick(), after the update finishes, the same tick() call that ran the update checker job also runs all the other jobs that would normally have happened during that time (the download can take quite long), without respecting the interval between those jobs! It just runs them in quick succession, which is not what I want. I want to be able to break out of the loop immediately after the update. It would work if each tick() call only executed at most 1 pending job.

And the jobs that didn't get to run in the meantime while one job is running (not this update job but in general) should be debounced (only ran once, one each, over the next N tick() calls).
The specified intervals for each job should not be shortened!

Date change can lead to high CPU usage, program crashes, and system instability.

When the date is changed from the current date to a future date, bad things can happen. This is related to the potential reetrancy issue mentioned (#5 & #8). In my case, I was spawning a new thread on each call, which caused a fork bomb.

I discovered this when I paused a virtual machine for a few days. Unpausing would cause 100% CPU usage and the VM would become unstable. After narrowing down the issue I tried just changing the date to one in the future, and sure enough, the issue popped up again. This could also occur if the system sleeps for a period of time, then wakes up.

Is time absolute or relative to scheduler start? / When will a job run the first time?

Is time absolute or relative to scheduler start?
IOW, is the first time that an added job is run immediately when the scheduler starts, or the next absolute time?
E.g. if I add this job to run every 5 minutes, will it run the first time when the minute part of the UTC time is a multiple of 5 after this (e.g. if I add the job at 14:04, will it run at 14:05?), or will it run first 5 minutes from the time when I add the job to the scheduler, or will it run immediately and then every 5 minutes from when I added it?

Update Crates.io

Hello,
thanks for your scheduler. Could you please update this crate on crates.io so I can switch back to using it from there instead of from git.
Thanks in Advance,
Chris

How to use async function in run thread?

How to use async function in run thread?
eg:

    let job = Job::new_repeated_async(Duration::from_secs(10), |_uuid, _l| {
        Box::pin(async move {
            let a = schedule::guahao::schedule_91160().await;
            println!("===> {}", a);
        })
    }).unwrap();

but report this error:

error: generator cannot be shared between threads safely
  --> src\main.rs:44:9
   |
44 | /         Box::pin(async move {
45 | |             let a = schedule::guahao::schedule_91160().await;
46 | |             println!("===> {}", a);
47 | |         })
   | |__________^ future created by async block is not `Sync`
   |
   = help: the trait `Sync` is not implemented for `(dyn std::future::Future<Output = Result<http::response::Response<hyper::body::body::Body>, hyper::error::Error>> + std::marker::Send + 'static)`
   = note: required for the cast to the object type `dyn std::future::Future<Output = ()> + Sync + std::marker::Send`

Not working with latest nightly (as of at least 2018-05-30)

First it required nightly rust, and then

  --> /home/trsh/.cargo/registry/src/github.com-1ecc6299db9ec823/cron-0.4.0/src/time_unit/mod.rs:18:23
   |
18 | use std::collections::range::{RangeArgument};
   |                       ^^^^^ Could not find `range` in `collections`

Working around `tick`

Hi! I noticed a crate had taken a dependency on cron so I came to check it out. I have a suggestion that's a bit involved, so forgive me in advance.

Currently the JobScheduler relies on the tick method to detect jobs that need to be run. This is functional but causes the program to claim a small amount of CPU time even when none of its jobs are active.

Each Schedule provides an upcoming() iterator. The DateTime values produced by this iterator are inherently sorted from soonest to most distant. Knowing this, you can:

  1. Make a new struct called, say, UpcomingJob that holds a DateTime and an Rc<Job>.
  2. Make an iterator type UpcomingJobIterator that provides next() by getting the next upcoming() DateTime from the Schedule and an Rc<Job> reference to the Job and combining them into an UpcomingJob.
  3. Implement Ord for UpcomingJob so they can be sorted in order of DateTime.
  4. Get an UpcomingJobIterator from each Job.
  5. Create a Heap.
  6. Pull the next() UpcomingJob from each iterator and put it in the heap (as ordered by DateTime)
  7. Peek at the top of the heap. That UpcomingJob is the next one to run across all of your Jobs.
  8. std::thread::sleep(...) until that fire time.
  9. Run the job.
  10. Remove that value from the top of the heap. Use the Rc<Job> reference in the UpcomingJob you just removed to get the next UpcomingJob for that Job and put it in the heap.
  11. Repeat steps 7-10.

The itertools crate offers a function called kmerge that should be able to take care of steps 5-11 for you.

Using this approach, your program is guaranteed to be asleep until the next fire time, no matter which job's next.

PS: Sorry about cron being nightly-only. It's mostly blocked on BTreeSet's range method being unstable. There's an issue tracking this.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.