Nothing
source(file.path("_helper", "init.R"))
source(file.path("aammrtf", "ref.R")); make_ref_obj_funs("item")
options(unitizer.color = FALSE)
# These tests are intended to cover all the functions/classes/methods in:
# - item.R
# - item.sub.R
# - test_eval.R # indirectly
# - heal.R
# - unitizer.R
# Basically everything that can be tested non-interactively
# Helper funs
callDep <- function(x) paste0(deparse(x@call, width.cutoff = 500),
collapse = "")
lsObjs <- function(x) paste0(x@ls$names, x@ls$status, collapse = ", ")
lsStat <- function(x) x@ls$status
lsInv <- function(x) isTRUE(attr(x@ls, "invalid"))
# Get started
new.exps <- expression(
1 + 1,
a <- 54, # keep
b <- 38, # keep
a + b,
e <- 5 * a, # keep
a ^ 2, # Keep
f <- e * a,
matrix(rep(f, 20)) # keep
)
ref.exps <- expression(
1 + 1,
a <- 54,
b <- 38,
a + b,
e <- 5 * a,
e ^ 3
)
Sys.sleep(0.2)
my.unitizer <- new("unitizer", id = 1, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer <- my.unitizer + ref.exps)
my.unitizer2 <- new("unitizer", id = 2, zero.env = new.env())
# now convert them to reference items
coi(my.unitizer2 <- my.unitizer2 + my.unitizer@items.new)
# now test against new.exps
coi(my.unitizer2 <- my.unitizer2 + new.exps)
# - "item funs" ----------------------------------------------------------------
item <- my.unitizer@items.new[[1L]]
unitizer:::itemType(item)
try(unitizer:::itemType(item) <- "asdfasd")
unitizer:::itemType(item) <- "reference"
unitizer:::itemType(item)
try(unitizer:::itemsType(my.unitizer@items.new) <- as.character(1:1000))
try(item$booboo)
# - "unitizer creation worked as expected" -------------------------------------
validObject(my.unitizer, complete = TRUE)
all.equal(capture.output(show(my.unitizer@items.new[[1L]])), rds(100))
identical(length(my.unitizer2), length(new.exps))
identical(length(my.unitizer2@items.new), length(new.exps))
identical(length(my.unitizer2@items.ref), length(ref.exps))
all.equal(
as.expression(
lapply(unitizer:::as.list(my.unitizer2@items.new), slot, "call")
),
new.exps
)
all.equal(
as.expression(
lapply(unitizer:::as.list(my.unitizer2@items.ref), slot, "call")
),
ref.exps
)
vals <- lapply(
unitizer:::as.list(my.unitizer2@items.new), function(x) x@data@value[[1L]]
)
vals.ign <- unitizer:::ignored(my.unitizer2@items.new)
all.equal(vals[!vals.ign], lapply(new.exps, eval)[!vals.ign])
all(vapply(vals[vals.ign], is, logical(1L), "unitizerDummy"))
vals <- lapply(
unitizer:::as.list(my.unitizer2@items.ref), function(x) x@data@value[[1L]]
)
vals.ign <- unitizer:::ignored(my.unitizer2@items.ref)
all.equal(vals[!vals.ign], lapply(ref.exps, eval)[!vals.ign])
all(vapply(vals[vals.ign], is, logical(1L), "unitizerDummy"))
my.unitizer2@items.new.map
my.unitizer2@items.ref.map
my.unitizer2@tests.fail
my.unitizer2@tests.status
my.unitizer2@section.map
unitizer:::ignored(my.unitizer2@items.new)
unitizer:::ignored(my.unitizer2@items.ref)
# - "Size Measurement works" ---------------------------------------------------
# Used to produce warnings because the same base.env was used for every
# unitizer because it was created on package load as part of the S4 class
# definition instead of in "initialize", so any time we instantiated more
# than one object they all shared the same environment, causing issues with
# saveRDS
x <- unitizer:::sizeUntz(my.unitizer2)
is.matrix(x) && is.numeric(x)
colnames(x)
# - "Environment healing works" ------------------------------------------------
items.mixed <- my.unitizer2@items.new[4:5] + my.unitizer2@items.ref[[1]] +
my.unitizer2@items.new[c(2, 6, 8)]
items.sorted <- unitizer:::healEnvs(items.mixed, my.unitizer2)
env.anc <- lapply(unitizer:::as.list(items.sorted), function(x) rev(unitizer:::env_ancestry(x@env,
my.unitizer2@base.env)))
max.len <- max(vapply(env.anc, length, 1L))
env.anc.2 <- lapply(env.anc, function(x) {
length(x) <- max.len
x
})
env.anc.df <- as.data.frame(env.anc.2, stringsAsFactors = FALSE)
# Here only the first item is reference, all others
length(unique(unlist(env.anc.df[2, ])))
all(
apply(
env.anc.df[-(1:2), -1], 1,
function(x) length(unique(Filter(Negate(is.na), x)))
) == 1L
)
# First item is reference, all others are new
unitizer:::itemsType(items.sorted)
# Expected order of ids
vapply(unitizer:::as.list(items.sorted), function(x) x@id, integer(1L))
lapply(unitizer:::as.list(items.sorted), function(x) x@ls$names)
unique(unlist(lapply(unitizer:::as.list(items.sorted), function(x) x@ls$status)))
# Tests with conditions
# - "Items with conditions" ----------------------------------------------------
my_fun <- function() {
warning("hello")
25
}
ref.exps1a <- expression(stop("boom"), my_fun())
my.unitizer1a <- new("unitizer", id = 100, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer1a <- my.unitizer1a + ref.exps1a)
all.equal(capture.output(show(my.unitizer1a@items.new[[1L]])), rds(200))
all.equal(capture.output(show(my.unitizer1a@items.new[[2L]])), rds(300))
all.equal(
capture.output(show(my.unitizer1a@items.new[[1L]]@data@conditions)), rds(400)
)
# - "Environment healing works 2" ----------------------------------------------
# Stars highlight items we are selecting, but keep in mind that unitizer only
# cares about non ignored tests, and that the selection status of ignored test
# has nothing to do with what we end up with wrt to ignored tests
new.exps2 <- expression(
1 + 1, # 1 *
a <- 54, # 2
b <- runif(5), # 3
howdy <- "yowser", # 4 *
a + b, # 5 *
e <- 5 * a, # 6
a ^ 2, # 7
f <- e * a, # 8
matrix(rep(f, 20)) # 9 *
)
ref.exps2 <- expression(
1 + 1, # 1
a <- 54, # 2
b <- runif(5), # 3 *
25 + 3, # 4
q <- b ^ 2 / a, # 5 *
a + b, # 6
z <- w <- list(1, 2, 3), # 7
Reduce(`+`, z), # 8 * Doesn't exist, should connect back to `a + b`
e <- 5 * a, # 9
e ^ 3, # 10 *
e * a # 11 *
)
# Note that healEnvs modifies objects that contain environments, and as such
# you won't get the same result if you run this function twice, so don't be
# surprised if tests fail in those circumstances
my.unitizer3 <- new("unitizer", id = 1, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer3 <- my.unitizer3 + ref.exps2)
my.unitizer4 <- new("unitizer", id = 2, zero.env = new.env())
# now convert them to reference items
coi(my.unitizer4 <- my.unitizer4 + my.unitizer3@items.new)
# now test against new.exps
coi(my.unitizer4 <- my.unitizer4 + new.exps2)
coi(
items.mixed2 <- my.unitizer4@items.ref[c(8, 10, 3, 5, 11)] +
my.unitizer4@items.new[c(1, 4, 5, 9)]
)
items.sorted2 <- unitizer:::healEnvs(items.mixed2, my.unitizer4)
env.anc <- lapply(unitizer:::as.list(items.sorted2), function(x) rev(unitizer:::env_ancestry(x@env,
my.unitizer4@base.env)))
max.len <- max(vapply(env.anc, length, 1L))
env.anc.2 <- lapply(env.anc, function(x) {
length(x) <- max.len
x
})
# oldest ancestor the same
env.anc.df <- as.data.frame(env.anc.2, stringsAsFactors = FALSE)
length(unique(unname(unlist(env.anc.df[1, ])))) # 1
# "base.env should be unitizer env")
identical(
env.anc.df[1, 1], unitizer:::env_name(my.unitizer4@base.env)
)
# "all tests should also have another sub base.env")
length(unique(unlist(env.anc.df[2, ]))) == 1L
# "and it should be the items.ref here")
identical(
env.anc.df[2, 1], unitizer:::env_name(my.unitizer4@items.ref@base.env)
)
items <- items.sorted2
items.lst <- unitizer:::as.list(items)
# "new items should all have normal status",
heal.info <- cbind(
type = unitizer:::itemsType(items), ignored = unitizer:::ignored(items),
id = vapply(items.lst, slot, 1L, "id"),
call = vapply(items.lst, callDep, ""),
ls = vapply(items.lst, lsObjs, ""),
ls.invalid = vapply(items.lst, lsInv, TRUE)
)
# ""
unique(unlist(lapply(items.lst[unitizer:::itemsType(items) == "new"], lsStat)))
# "Reference tests should have no ls data",
unique(vapply(items.lst[unitizer:::ignored(items)], lsObjs, ""))
all(vapply(items.lst[unitizer:::ignored(items)], lsInv, logical(1L)))
# - "ls works" -----------------------------------------------------------------
my.unitizer5 <- new("unitizer", id = 2, zero.env = new.env())
# now add back our composite elements as references
coi(my.unitizer5 <- my.unitizer5 + items.sorted2)
# and new items
coi(my.unitizer5 <- my.unitizer5 + new.exps2)
# This is an ignored test, so there will be some problems
env.val <- new.env(parent = my.unitizer5@items.new[[3]]@env)
env.eval <- new.env(parent = env.val)
assign(".NEW", my.unitizer5@items.new[[3]], env.val)
assign(".new", my.unitizer5@items.new[[3]]@data@value[[1L]],
env.val)
assign(".REF", my.unitizer5@items.ref[[my.unitizer5@items.new.map[[3]]]],
env.val)
assign(".ref", my.unitizer5@items.ref[[my.unitizer5@items.new.map[[3]]]]@data@value[[1L]],
env.val)
ls.res <- evalq(unitizer:::unitizer_ls(), env.eval) # warn
# Reference tests won't show up since they were nuked by `healEnvs`
all.equal(ls.res, rds(500))
# These are normal tests so should work
env.val <- new.env(parent = my.unitizer5@items.new[[9]]@env)
env.eval <- new.env(parent = env.val)
assign(".NEW", my.unitizer5@items.new[[9]], env.val)
assign(".new", my.unitizer5@items.new[[9]]@data@value[[1L]],
env.val)
assign(".REF", my.unitizer5@items.ref[[my.unitizer5@items.new.map[[9]]]],
env.val)
assign(".ref", my.unitizer5@items.ref[[my.unitizer5@items.new.map[[9]]]]@data@value[[1L]],
env.val)
all.equal(evalq(unitizer:::unitizer_ls(), env.eval),
rds(600))
all.equal(capture.output(print(evalq(unitizer:::unitizer_ls(),
env.eval))), rds(700))
# - "Environment Healing Works #3" ---------------------------------------------
#
# Main difference to previous versions is that we're testing that moving the
# order of tests around between ref and new still works
#
# Test that reference tests moving around doesn't cause major issues
new.exps6 <- expression(
1 + 1, # 1 *
a <- 54, # 2
b <- runif(5), # 3
howdy <- "yowser", # 4
a + b, # 5
e <- 5 * a, # 6
a ^ 2, # 7 *
f <- 25, # 8 *
matrix(rep(f, 20)) # 9
)
ref.exps6 <- expression(
1 + 1, # 1
a <- 54, # 2
f <- 25, # 3
matrix(rep(f, 20)), # 4 *
b <- runif(5), # 5
boomboom <- "boo", # 6
a + b, # 7 *
a + b + f, # 8
e <- 5 * a, # 9
a ^ 2 # 10
)
my.unitizer10 <- new("unitizer", id = 1, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer10 <- my.unitizer10 + ref.exps6)
my.unitizer11 <- new("unitizer", id = 2, zero.env = new.env())
# now convert them to reference items
coi(my.unitizer11 <- my.unitizer11 + my.unitizer10@items.new)
# now test against new.exps
coi(my.unitizer11 <- my.unitizer11 + new.exps6)
items.mixed3 <- my.unitizer11@items.ref[c(4, 7)] +
my.unitizer11@items.new[c(1, 7, 8)]
items.sorted3 <- unitizer:::healEnvs(items.mixed3, my.unitizer11)
# Both reference tests get appended to item #1, which means among other things
# that for the second refernce test, the `a` object is absent (but `b` is
# present because it gets sucked in by virtue of being an ignored test just
# ahead of it)
items <- items.sorted3
items.lst <- unitizer:::as.list(items)
cbind(
type = unitizer:::itemsType(items), ignored = unitizer:::ignored(items),
id = vapply(items.lst, slot, 1L, "id"),
call = vapply(items.lst, callDep, ""),
ls = vapply(items.lst, lsObjs, ""),
ls.invalid = vapply(items.lst, lsInv, TRUE)
)
# - "No circular environment references" ---------------------------------------
# This is to test for issue #2, which resulted in a self referential environment
# in the stored items. The following code used to fail:
new.exps3 <- expression(1 + 1, a <- 54, b <- 5, 2 + 2, runif(1))
ref.exps3 <- expression(1 + 1, a <- 54, 2 + 2, runif(1))
my.unitizer6 <- new("unitizer", id = 1, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer6 <- my.unitizer6 + ref.exps3)
my.unitizer7 <- new("unitizer", id = 2, zero.env = new.env())
# now convert them to reference items
coi(my.unitizer7 <- my.unitizer7 + my.unitizer6@items.new)
# now test against new.exps
coi(my.unitizer7 <- my.unitizer7 + new.exps3)
# Note this doesn't test that there are no circular references, only that what
# used to fail no longer fails.
cbind(my.unitizer7@tests.new, my.unitizer7@tests.result)
# - "testFuns" -----------------------------------------------------------------
# Error objects
# these two should just work fine
is(new("testFuns", output = all.equal, value = function(x, y) TRUE), "testFuns")
is(new("testFuns"), "testFuns")
try(new("testFuns", output = all.equal, value = function(x, y, z) TRUE))
# this should work too now, since technically has two args
is(
new("testFuns", output = all.equal, value = function(x, y = 1, z = 1) TRUE),
"testFuns"
)
try(new("testFuns", cabbage = all.equal))
# - "Misc" ---------------------------------------------------------------------
new.exps4 <- expression(a <- function() b(), b <- function() TRUE, a())
my.unitizer8 <- new("unitizer", id = 3, zero.env = new.env())
new.exps5 <- expression(a <- function() b(), NULL, b <- function() TRUE, a())
my.unitizer9 <- new("unitizer", id = 4, zero.env = new.env())
coi(x <- my.unitizer9 + new.exps5)
local({
fun <- function() quote(stop("This error should not be thrown"))
is(
new(
"unitizerItem", value = fun(), call = quote(fun()),
env = sys.frame(sys.parent() + 1L)
),
"unitizerItem"
)
})
# Nested environment hand waving can break down under certain circumstances
# this first one should work because there are no tests until after all
# the pieces necessary to run `a()` are defined:
coi(res <- my.unitizer8 + new.exps4)
is(res, "unitizer")
# this should break because the NULL forces `b` to be stored in a different
# environment to `a`; note: funky error message matching because in
# at least some versions of rdevel reported fun name seems to change
# (possibly related to level 3 bytecode)
# could not find fun
x@items.new[[4]]@data@message[[1]]
# - "Comparison Function Errors" -----------------------------------------------
exps <- expression(fun <- function(x, y) warning("not gonna work"),
unitizer_sect(compare = fun, expr = {
1 + 1
}))
my.unitizer <- new("unitizer", id = 25, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer <- my.unitizer + exps)
coi(my.unitizer2 <- new("unitizer", id = 26, zero.env = new.env()) +
my.unitizer@items.new)
# warn: not gonna work
coi(my.unitizer2 <- my.unitizer2 + exps)
as.character(my.unitizer2@tests.status)
my.unitizer2@tests.errorDetails[[2]]@value@value
# - "Language Objects Tested Properly" -----------------------------------------
exps <- expression(quote(x), quote(x + y), quote(identity(x)),
expression(1 + y), quote(expression(1 + y)))
my.unitizer <- new("unitizer", id = 27, zero.env = new.env())
# add ref.exps as new items
coi(my.unitizer <- my.unitizer + exps)
coi(my.unitizer2 <- new("unitizer", id = 28, zero.env = new.env()) +
my.unitizer@items.new)
coi(my.unitizer2 <- my.unitizer2 + exps)
# This used to error b/c expressions returning unevaluated calls/symbols were
# not compared as such (they were evaluated)
as.character(my.unitizer2@tests.status)
# - "Test Fun Captured Properly" -----------------------------------------------
new("unitizerItemTestFun", fun = identical)@fun.name
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.