From hb at biostat.ucsf.edu  Mon Jan 26 19:53:37 2015
From: hb at biostat.ucsf.edu (Henrik Bengtsson)
Date: Mon, 26 Jan 2015 10:53:37 -0800
Subject: [Rd] Inspect a "delayed" assigned whose value throws an error?
Message-ID: <CAFDcVCQiE=DEJuNMAd2xZfQF-Cz3fyx4ajTwmeBvncwmcsS8oA@mail.gmail.com>

Hi, I got an interesting programming challenge:

How do you inspect an object which is assigned via delayedAssign() and
that throws an error as soon as it is "touched" (=the value is
evaluated)?  Is it possible?


MINIMAL EXAMPLE:

$ R --vanilla
> delayedAssign("foo", stop("Hey!"))

(If you find this minimal example silly/obvious, please skip down to
the real example at the end)

> foo
Error: Hey!

> str(foo)
Error in str(foo) : Hey!
In addition: Warning message:
In str(foo) : restarting interrupted promise evaluation

> mode(foo)
Error in mode(foo) : Hey!
In addition: Warning message:
In mode(foo) : restarting interrupted promise evaluation

> .Internal(inspect(foo))
Error: Hey!
In addition: Warning message:
restarting interrupted promise evaluation

> traceback()
1: stop("Hey!")

Is there anyway I can inspect this object using the R API without
evaluating the value in the delayed assignment?  Is it possible to
test if this is a delayed assigned or not?


BACKGROUND:
The background to this is where I have a function in the R.oo package
that scans namespaces for functions with a certain class attribute.
For this I use is.function() and inherits() to inspect each object.
An aroma.affymetrix user reported on a problem that boiled down to the
following:

# source("http://bioconductor.org/biocLite.R"); biocLite("hgu133a.db")
> library("hgu133a.db")
> is.function(hgu133aPFAM)
Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM
  or PROSITE accessions.
> .Internal(inspect(hgu133aPFAM))

> traceback()
3: stop(paste(msg, collapse = ""), call. = FALSE, domain = NA)
2: .Defunct(msg = msg)
1: (function ()
   {
       if (grepl("PFAM", x)) {
           bimapName <- paste0(prefix, "PFAM")
       }
       else {
           bimapName <- paste0(prefix, "PROSITE")
       }
       x <- dc[[bimapName]]
       msg = wmsg(paste0(bimapName, " is defunct. ", "Please use select() if you
 need access to PFAM or PROSITE accessions. \n"))
       if (interactive()) {
           .Defunct(msg = msg)
       }
   })()

My immediate solution is to perform those tests using tryCatch(), but
this is interesting, because this function is such that the error is
only thrown in interactive() sessions, i.e. the following works:

$ Rscript -e "hgu133a.db::hgu133aPFAM"
[...]
NULL

This is probably also why none of my aroma.affymetrix system tests
caught this.  Without tracing the source code behind, which seems
quite nested, the above is why I believe the assignment is "delayed";
traceback() shows a body source code, the object evaluates to
different things depending on interactive().

/Henrik



[Rd] Inspect a "delayed" assigned whose value throws an error?
Henrik Bengtsson