30

I am trying to code a set of functions to check for missing R packages, and to install them if necessary. There's some good code to do that at StackOverflow: start here.

I would like to make the functions as silent as possible, especially since R returns even successful messages in red ink. Accordingly, I have tried to pass the quietly = TRUE argument to both library and require.

However, these options never seem to work:

# attempt to get a silent fail
require(xyz, quietly = TRUE)
Warning message:
In library(package, lib.loc = lib.loc, character.only = TRUE, logical.return = TRUE,  :
  there is no package called ‘xyz’

How can I get require to fail silently, and what am I not getting about the quietly option?

The documentation says:

quietly a logical. If TRUE, no message confirming package loading is printed, and most often, no errors/warnings are printed if package loading fails.

But it seems to me "most often" should be "almost never" in my personal experience. I would happily hear about your experience with that. Rationale: coding functions to help students.


Add. The same question applies to quiet = TRUE in install.packages(). It kills only the progress bar, but not the "downloaded binary packages are in" message (printed in black, yay!) that follows, even though it has no use to the median user.


Add. In case this might be of interest to anyone, the code so far:

## getPackage(): package loader/installer
getPackage <- function(pkg, load = TRUE, silent = FALSE, repos = "http://cran.us.r-project.org") {
  if(!suppressMessages(suppressWarnings(require(pkg, character.only = TRUE, quietly = TRUE)))) {
    try(install.packages(pkg, repos = repos), silent = TRUE)
  }
  if(load) suppressPackageStartupMessages(library(pkg, character.only = TRUE, quietly = TRUE))
  if(load & !silent) message("Loaded ", pkg)
}

## Not run:
x <- c("ggplot2", "devtools") # etc.
lapply(x, getPackage, silent = TRUE)

I'm thinking of just quitting the effort to use quietly in the function above, given that it does not seem to work when expected. I should probably ask the R userlists about that to get an explanation from the core devteam. The suppressMessages(suppressWarnings(require(...))) workaround can be unstable in my experience.

Community
  • 1
  • 1
Fr.
  • 2,865
  • 2
  • 24
  • 44
  • 10
    +1 for "most often" should be "almost never"! – agstudy Feb 12 '13 at 14:33
  • 1
    You might want to read the source code for `require` and `library` to see exactly what `quietly` does. Unfortunately those functions are a mess of spaghetti code. Also read the source code for `install.packages` to see how complicated (unzip a file into a directory) you can make a simple process. – hadley Feb 13 '13 at 13:01
  • 1
    I have read the source for `require`: it's a lot of nested conditionals. The `quietly` argument kills additional error information, but does not suppress the `Loading...` messages. Students find it bothering, especially in red ink. One of R's idiosyncrasies. My favourite is the information passed by `install.packages` at the end, probably with `cat`: "The downloaded packages are now in (temporary and incomprehensible folder path)". – Fr. Feb 14 '13 at 05:58

6 Answers6

23

If you want to make your require function very quiet, you can use :

suppressMessages(suppressWarnings(require(xyz)))

Which gives :

...well, nothing :)

juba
  • 47,631
  • 14
  • 113
  • 118
  • 4
    This is what I have ended up doing until now. However, it can be unstable: I have had RStudio abort my R session quite a few times when running this, especially through a `lapply` structure. – Fr. Feb 12 '13 at 14:42
  • 2
    @Fr. Always check that sort of error outside of RStudio to make sure it isn't simply specific to that particular IDE. – joran Feb 12 '13 at 15:27
  • I have checked it outside of RStudio, and it's stable in R64. – Fr. Feb 12 '13 at 15:31
  • 1
    Then it sounds like the RStudio guys would probably like to hear about it, if it's a reproducible crash. It doesn't happen for me with version 0.97.310 on Ubuntu 12.04. – Ben Bolker Feb 12 '13 at 15:32
  • I got the crashes while trying to install a 60+ list of packages through a code structure that I have rewritten since. If I manage to get a reproducible error, I'll certainly file a report about it. – Fr. Feb 12 '13 at 15:39
20

I'm not sure exactly when this was added to the language, but the preferred way to do this nowadays is

suppressPackageStartupMessages({
    require(this)
    require(that)
    ...
})

This zorches "Loading ...", complaints about masking symbols, and other noise, but messages indicating actual problems still appear (e.g. a package or dependency is unavailable).

zwol
  • 135,547
  • 38
  • 252
  • 361
8

The simplest solution appears to be

try(library(xyz), silent=TRUE)

require is basically a wrapper around tryCatch(library), so this just cuts out some extraneous code.

Hong Ooi
  • 56,353
  • 13
  • 134
  • 187
1

One workaround is to set warn options, before and after the call...

 options(warn=-1)
 try(require(xyz, quietly = TRUE),silent=TRUE)
 options(warn=0)

But this is dangerous.. I think what you need is to change the color of warning message.

agstudy
  • 119,832
  • 17
  • 199
  • 261
  • This is indeed dangerous and not recommendable, although I agree that it works. But to me, it's just too hacky – almost as much as setting the warnings text to background color. – Fr. Feb 12 '13 at 14:44
  • @Fr. I guess you want to hide this for yours no technical user.. I am trying to find an option to change the warning message to green for example.. – agstudy Feb 12 '13 at 14:47
  • God luck with that. For some reason, `message()` and `warning()` are printed identically. It's only with `cat()` that you can print neutral text. I don't think the colors are hard-coded. – Fr. Feb 12 '13 at 14:50
1
PkgNames <- c("forecast", "tseries", "ggplot2", "qcc", "ggmap","corrgram",
              "effects", "Hmisc", "plyr", "reshape")
invisible(suppressMessages(suppressWarnings(lapply(PkgNames, require, character.only = T))))
demongolem
  • 9,474
  • 36
  • 90
  • 105
0

This is an old question, but for the benefit of anyone else looking for an answer:

requireNamespace with quietly=TRUE seems to quietly check if the package is installed, so checking that can be quiet:

    > if (requireNamespace("Foobar", quietly = TRUE)) "Found it" else "Not found"
    [1] "Not found"
    > if (requireNamespace("utils", quietly = TRUE)) "Found it" else "Not found"
    [1] "Found it"

So to solve the OP's primary problem (the question in bold):

    if (requireNamespace("package", quietly=TRUE)) require("package", quietly=TRUE);

Any noise comes from loading the package. The second quietly=TRUE helps somewhat. So, the above is silent for missing packages, silent for some found packages, much less noisy than without quietly for others. There are undoubtedly packages for which is doesn't help at all.

Bradley
  • 53
  • 5