diff --git a/CHANGELOG.md b/CHANGELOG.md index 3db0a8b..4df7cf8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,11 +7,12 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [v2.0.1] -This patch release of `wf-transcriptomes` handles an additional quantification failure case that was not observed before release. -Users of wf-transcriptomes v2.0.0 who have encountered issues during quantification should adopt this release. +This patch release of `wf-transcriptomes` handles an additional quantification failure edge case that was not observed before release, and fixes an issue encountered during joint discovery for many samples. +Users of wf-transcriptomes v2.0.0 who have encountered issues during discovery and quantification should adopt this release. ### Fixed -- Error in full_join encountered during runPerSampleBambuQuant when all read classes have no compatible transcript assignment. +- "Error in full_join" encountered during `runPerSampleBambuQuant` when all read classes have no compatible transcript assignment. An empty quant table is correctly emitted instead. +- "unable to find an inherited method for function 'rowData'" encountered during `runJointBambuDiscover` when providing many samples. The workflow now correctly handles data spilled to disk by bambu discover. ## [v2.0.0] diff --git a/bin/workflow_glue_r/R/bambu.R b/bin/workflow_glue_r/R/bambu.R index 0f2c003..81f3c03 100644 --- a/bin/workflow_glue_r/R/bambu.R +++ b/bin/workflow_glue_r/R/bambu.R @@ -280,6 +280,22 @@ bambu_normalise_rc_file_list <- function(rc_files, aliases = NULL) { rc_files } +bambu_load_rc_file <- function(rc_file) { + if (is.character(rc_file) && length(rc_file) == 1L) { + rc_file <- readRDS(rc_file) + } + if (!methods::is(rc_file, "RangedSummarizedExperiment")) { + stop( + sprintf( + "Expected bambu read-class output to be a RangedSummarizedExperiment or RDS path, got '%s'.", + paste(class(rc_file), collapse = ", ") + ), + call. = FALSE + ) + } + rc_file +} + bambu_chunk_id_for_seqname <- function(seqname) { seqname <- as.character(seqname) seqname <- gsub("[^A-Za-z0-9._-]+", "_", seqname) @@ -293,6 +309,8 @@ bambu_chunk_id_for_seqname <- function(seqname) { bambu_chunk_rc_files <- function(rc_files, aliases, sample_df) { rc_files <- bambu_normalise_rc_file_list(rc_files, aliases = aliases) + # bambu may provide a RangedSummarizedExperiment or a path to an RDS spilled to disk [CW-7338] + rc_files <- lapply(rc_files, bambu_load_rc_file) seqnames <- unique(unlist(lapply(rc_files, function(rcf) { as.character(SummarizedExperiment::rowData(rcf)$chr.rc) }))) diff --git a/bin/workflow_glue_r/tests/testthat/test_bambu.R b/bin/workflow_glue_r/tests/testthat/test_bambu.R index 0d05d7f..8e04b41 100644 --- a/bin/workflow_glue_r/tests/testthat/test_bambu.R +++ b/bin/workflow_glue_r/tests/testthat/test_bambu.R @@ -383,6 +383,33 @@ testthat::test_that("discover mode writes chunked rc outputs", { testthat::expect_equal(chunk_bundle$aliases, c("sampleA", "sampleB")) }) +testthat::test_that("cw-7338 chunking accepts path-backed rc outputs", { + fixture_dir <- tempfile("bambu-path-backed-rc-") + dir.create(fixture_dir) + + make_rc_sample <- function(alias) { + rcf <- make_test_tx_se(sample_names = alias) + S4Vectors::mcols(SummarizedExperiment::rowRanges(rcf))$chr.rc <- c("chr1", "chr1", "chr2", "chr2") + rcf + } + + rc_paths <- file.path(fixture_dir, paste0(c("sampleA", "sampleB"), "_readClassSe.rds")) + saveRDS(make_rc_sample("sampleA"), rc_paths[[1]]) + saveRDS(make_rc_sample("sampleB"), rc_paths[[2]]) + names(rc_paths) <- c("sampleA", "sampleB") + + chunk_bundles <- bambu_chunk_rc_files( + as.list(rc_paths), + aliases = c("sampleA", "sampleB"), + sample_df = data.frame(alias = c("sampleA", "sampleB"), stringsAsFactors = FALSE) + ) + + testthat::expect_equal(unname(sort(vapply(chunk_bundles, `[[`, character(1), "seqname"))), c("chr1", "chr2")) + testthat::expect_equal(chunk_bundles[[1]]$aliases, c("sampleA", "sampleB")) + testthat::expect_s4_class(chunk_bundles[[1]]$rc_files$sampleA, "RangedSummarizedExperiment") + testthat::expect_s4_class(chunk_bundles[[1]]$rc_files$sampleB, "RangedSummarizedExperiment") +}) + testthat::test_that("annotation tx counts are computed once per seqname", { discovered_annotations <- GenomicRanges::GRangesList( tx1 = GenomicRanges::GRanges(seqnames = "chr1", ranges = IRanges::IRanges(c(1, 10), width = 5)),