Allow alabaster applications to divert to a different staging generic from stageObject.

altStageObject(...)

altStageObjectFunction(generic)

Arguments

...

Further arguments to pass to stageObject or an equivalent generic.

generic

Generic function that can serve as a drop-in replacement for stageObject.

Value

For altStageObject, a named list similar to the return value of stageObject.

For altStageObjectFunction, the alternative generic (if any) is returned if generic is missing. If generic is provided, it is used to define the alternative, and the previous alternative is returned.

Details

altStageObject is just a wrapper around stageObject that responds to any setting of altStageObjectFunction. This allows applications to inject customizations into the staging process, e.g., to store more metadata to particular objects. Developers of alabaster extensions should use altStageObject to stage child objects when writing their stageObject methods, to ensure that application-specific customizations are respected for the children.

To motivate the use of altStageObject, consider the following scenario.

  1. We have created a staging method for class X, defined for the stageObject generic.

  2. An alabaster application Y requires the addition of some custom metadata during the staging process for X. It defines an alternative staging generic stageObject2 that, upon encountering an instance of X, redirects to a application-specific method. For example, the stageObject2 method for X could call X's stageObject method, add the necessary metadata to the result, and then return the list.

  3. When operating in the context of application Y, the stageObject2 generic is used to set altStageObjectFunction. Any calls to altStageObject in Y's context will subsequently call stageObject2.

  4. So, when writing a stageObject method for any objects that might include X as children, we use altStageObject instead of directly using stageObject. This ensures that, if a child instance of X is encountered and we are operating in the context of application Y, we correctly call stageObject2 and then ultimately the application-specific method.

Note for application developers: the alternative stageObject2 method for X should not call altStageObject on the same instance of X. Doing so will introduce an infinite recursion where altStageObject calls stageObject2 that then calls altStageObject, etc. Rather, developers should call stageObject directly in such cases. For child objects, no infinite recursion will occur and either stageObject2 or altStageObject can be used.

Author

Aaron Lun

Examples

old <- altStageObjectFunction()

# Creating a new generic for demonstration purposes:
setGeneric("superStageObject", function(x, dir, path, child=FALSE, ...)
    standardGeneric("superStageObject"))
#> [1] "superStageObject"

setMethod("superStageObject", "ANY", function(x, dir, path, child=FALSE, ...) {
    print("Falling back to the base method!")
    stageObject(x, dir, path, child=child, ...)
})

altStageObjectFunction(superStageObject)

# Staging an example DataFrame. This should print our message.
library(S4Vectors)
df <- DataFrame(A=1:10, B=LETTERS[1:10])
tmp <- tempfile()
dir.create(tmp)
out <- altStageObject(df, tmp, path="coldata")
#> [1] "Falling back to the base method!"

# Restoring the old loader:
altStageObjectFunction(old)