Skip to content
Prev 61086 / 63421 Next

[External] Time to drop globalenv() from searches in package code?

Excluding the global environment, and all its parent environments from
the search path that a package sees would be great news, because it
would makes things more robust and probably detect a few more bugs out
there.  In addition to the use case that Duncan mentions, it would
also remove the ambiguity that comes from searching attached packages
for global/free variables.

Speaking of the latter, isn't it time to escalate the following to a WARNING?

* checking R code for possible problems ... NOTE
my_fcn: no visible global function definition for ?var?
Undefined global functions or variables:
  var
Consider adding
  importFrom("stats", "var")
to your NAMESPACE file.

There are several package on Bioconductor with such mistakes, and I
can imagine there are still some old CRAN package too that haven't
gone from "recent" CRAN incoming checks. The problem here is that the
intended `var` can be overridden in the global environment, in a
third-party attached package, or in any other environment on the
search() path.

Regarding:
This should be coved by 'R CMD check', also without --as-cran; if we use:

hello <- function() {
  msg <- "Hello world!"
  if (require("tools")) msg <- toTitleCase(msg)
  message(msg)
}

we get:

* checking dependencies in R code ... NOTE
'library' or 'require' call to ?tools? in package code.
  Please use :: or requireNamespace() instead.
  See section 'Suggested packages' in the 'Writing R Extensions' manual.?
...
* checking R code for possible problems ... NOTE
hello: no visible global function definition for ?toTitleCase?
Undefined global functions or variables:
  toTitleCase

This should be enough for a package developer to figure out that the
function should be implemented as:

hello <- function() {
  msg <- "Hello world!"
  if (requireNamespace("tools")) msg <- tools::toTitleCase(msg)
  message(msg)
}

which passes 'R CMD check' with all OK.


BTW, is there a reason why one cannot import from the 'base' package?
If we add, say, importFrom(base, mean) to a package's NAMESPACE file,
the package builds fine, but fails to install;

$ R --vanilla CMD INSTALL teeny_0.1.0.tar.gz
* installing to library ?/home/hb/R/x86_64-pc-linux-gnu-library/4.2-CBI-gcc9?
* installing *source* package ?teeny? ...
** using staged installation
** R
** byte-compile and prepare package for lazy loading
Error in asNamespace(ns, base.OK = FALSE) :
  operation not allowed on base namespace
Calls: <Anonymous> ... namespaceImportFrom -> importIntoEnv ->
getNamespaceInfo -> asNamespace
Execution halted
ERROR: lazy loading failed for package ?teeny?

Is this by design (e.g. more flexibility in maintaining the base-R
packages), or due to a technical limitation (e.g. the 'base' package
is not fully loaded at this point)?

/Henrik
On Sat, Sep 17, 2022 at 1:24 PM <luke-tierney at uiowa.edu> wrote: