naptime: A Flexible and Robust Sys.sleep() Replacement

Russell S. Pierce & Timothy Gann

2017-02-22

Why should I use it?

naptime makes delaying code execution in R more flexible and robust. It makes delaying code execution more flexible by supporting more data types than base::Sys.sleep(). It makes delaying code more robust by allowing errors in the delay specification to throw warnings instead of errors. Most notably, because naptime supports more input data types, you can use package:lubridate functions in conjunction with naptime to yield human readable time delays and intervals.

Consider the case of waiting one hour:

Sys.sleep(3600)

# versus

naptime(lubridate::hours(1))

Consider the case of wanting to start processing every hour for a job of an indeterminate duration:

repeat{
  start_time <- lubridate::now()
  # Do processing
  sleep_duration <- 3600 - as.numeric(lubridate::now() - start_time)
  if (sleep_duration > 0) {
    Sys.sleep(sleep_duration)
  }
}

# versus

repeat{
  start_time <- lubridate::now()
  # Do processing
  naptime(start_time + lubridate::hours(1))
}

How do I use it?

Because naptime() has nearly identical arguments and behavior as base::Sys.sleep() in response to numeric inputs, it can be nearly used as a drop-in replacement for base::Sys.sleep().

There are two notable differences in the behavior of Sys.sleep() and naptime():

Options

All options are set via base::options().

Polymorphic inputs

naptime() accepts a wide variety of inputs.

Polymorphism for:

naptime(1)
#> NULL
naptime(lubridate::now(tzone = "UTC")+lubridate::seconds(1))
#> NULL
naptime(lubridate::seconds(1))
#> NULL
naptime(as.character(lubridate::now() + lubridate::seconds(1)))
#> NULL
naptime(difftime(lubridate::now() + lubridate::seconds(1), lubridate::now()))
#> NULL
naptime(TRUE)
#> NULL
naptime(NULL)
#> NULL
naptime(glm(rnorm(5) ~ runif(5)), permissive = TRUE)
#> Warning: The time paramater was not scalar (length equal to 1)
#> Warning: unhandled input for naptime(): Error in (function (classes, fdef, mtable) : unable to find an inherited method for function 'naptime' for signature '"list"'
#> NULL
options(naptime.permissive = TRUE)
naptime(glm(rnorm(5) ~ runif(5)))
#> Warning: The time paramater was not scalar (length equal to 1)

#> Warning: unhandled input for naptime(): Error in (function (classes, fdef, mtable) : unable to find an inherited method for function 'naptime' for signature '"list"'
#> NULL

If you find a reasonable input-type for which naptime::naptime() doesn’t have a reasonable response, please file an issue or PR in which you resolve the shortcoming.

How do I get it?

The current version is on CRAN, but you can fetch an early release of the upcoming build directly from github:

library(devtools)
install_github("drknexus/naptime")
library(naptime)

Author’s Note

The initial draft of this code was written by Timothy Gann under a spec drafted by Russell Pierce. Many improvements and bug fixes to the original code, all packaging, and all tests were written by Russell Pierce. Russell Pierce is the current maintainer and responsible party for this package.