diff --git a/NEWS.md b/NEWS.md index f1787cd20..a2a68e80f 100644 --- a/NEWS.md +++ b/NEWS.md @@ -1,5 +1,9 @@ # teal.slice 0.7.1.9003 +### Enhancements + +* Relaxed assertions on `teal_slices` to ignore duplicated `teal_slice` elements. + # teal.slice 0.7.1 ### Miscellaneous diff --git a/R/teal_slices.R b/R/teal_slices.R index 9b1bebfc8..f527c4a76 100644 --- a/R/teal_slices.R +++ b/R/teal_slices.R @@ -94,10 +94,12 @@ teal_slices <- function(..., allow_add = TRUE) { slices <- list(...) checkmate::assert_list(slices, types = "teal_slice", any.missing = FALSE) + hashes <- vapply(slices, function(x) rlang::hash(isolate(as.list(x))), character(1)) + slices <- slices[!duplicated(hashes)] slices_id <- isolate(vapply(slices, `[[`, character(1L), "id")) if (any(duplicated(slices_id))) { stop( - "Some teal_slice objects have the same id:\n", + "Conflicting `teal_slice` objects id. Items have the same id but their settings differ:\n", toString(unique(slices_id[duplicated(slices_id)])) ) } @@ -199,11 +201,11 @@ c.teal_slices <- function(...) { all_attributes <- lapply(x, attributes) all_attributes <- coalesce_r(all_attributes) all_attributes <- all_attributes[names(all_attributes) != "class"] - + slices <- unlist(x, recursive = FALSE) do.call( teal_slices, c( - unique(unlist(x, recursive = FALSE)), + slices, all_attributes ) ) diff --git a/tests/testthat/test-teal_slices.R b/tests/testthat/test-teal_slices.R index 63ba6f9b9..ac2e451c4 100644 --- a/tests/testthat/test-teal_slices.R +++ b/tests/testthat/test-teal_slices.R @@ -21,8 +21,6 @@ testthat::test_that("teal_slices checks arguments", { testthat::expect_error(teal_slices(fs1, fs2, count_type = c("all", "none"))) testthat::expect_error(teal_slices(fs1, fs2, allow_add = NULL), "Assertion on 'allow_add' failed") - - testthat::expect_error(teal_slices(fs1, fs1, fs2), "Some teal_slice objects have the same id") }) testthat::test_that("teal_slices returns `teal_slices`", { @@ -45,6 +43,24 @@ testthat::test_that("teal_slices returns `teal_slices`", { testthat::expect_length(teal_slices(fs1, fs2), 2L) }) +testthat::test_that("teal_slices accepts duplicated elements if they have identical values", { + ts1 <- teal_slice(dataname = "ds1", varname = "var1", id = "slice1") + ts2 <- teal_slice(dataname = "ds1", varname = "var1", id = "slice1") + + testthat::expect_no_error(teal_slices(ts1, ts2)) +}) + +testthat::test_that("teal_slices throw an error if elements with duplicated id have different settings", { + ts1 <- teal_slice(dataname = "ds1", varname = "var1", id = "slice1") + ts2 <- teal_slice(dataname = "ds1", varname = "var2", id = "slice1") + + testthat::expect_error( + teal_slices(ts1, ts2), + "Conflicting `teal_slice` objects id. Items have the same id but their settings differ:\nslice1" + ) +}) + + testthat::test_that("teal_slices raises error when include_varnames and exclude_varnames specified same dataset", { testthat::expect_error( teal_slices( @@ -266,6 +282,7 @@ testthat::test_that("c.teal_slices concatenates `teal_slices` objects", { testthat::expect_length(c(fss1, fss2), length(fss1) + length(fss2)) }) + testthat::test_that("c.teal_slices coalesces attributes", { fs1 <- teal_slice("data1", "var1") fs2 <- teal_slice("data1", "var2")