Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implementing targets for SpatRasterCollection: tar_terra_sprc() #50

Merged
merged 2 commits into from
Apr 19, 2024
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions NAMESPACE
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
export(geotargets_option_get)
export(geotargets_option_set)
export(tar_terra_rast)
export(tar_terra_rasts)
export(tar_terra_vect)
importFrom(rlang,"%||%")
importFrom(rlang,arg_match0)
Expand Down
160 changes: 160 additions & 0 deletions R/tar-terra-rasts.R
Original file line number Diff line number Diff line change
@@ -0,0 +1,160 @@
#' Create a terra _SpatRasterCollection_ target
#'
#' Provides a target format for [terra::SpatRasterCollection] objects,
#' which have no restriction in the extent or other geometric parameters.
#'
#' @param filetype character. File format expressed as GDAL driver names passed
#' to [terra::writeRaster()]
#' @param gdal character. GDAL driver specific datasource creation options
#' passed to [terra::writeRaster()]
#' @param ... Additional arguments not yet used
#'
#' @inheritParams targets::tar_target
#' @seealso [targets::tar_target_raw()]
#' @author Andrew Gene Brown
#' @author Nicholas Tierney
#' @export
#' @examples
#' if (Sys.getenv("TAR_LONG_EXAMPLES") == "true") {
#' targets::tar_dir({ # tar_dir() runs code from a temporary directory.
#' library(geotargets)
#' targets::tar_script({
#' elev_scale <- function(z = 1, projection = "EPSG:4326") {
#' terra::project(
#' terra::rast(system.file("ex", "elev.tif", package = "terra")) * z,
#' projection
#' )
#' }
#' list(
#' tar_terra_rasts(
#' raster_elevs,
#' # two rasters, one unaltered, one scaled by factor of 2 and
#' # reprojected to interrupted good homolosine
#' command = terra::sprc(list(
#' elev_scale(1),
#' elev_scale(2, "+proj=igh")
#' ))
#' )
#' )
#' })
#' targets::tar_make()
#' x <- targets::tar_read(raster_elevs)
#' })
#' }
tar_terra_rasts <- function(name,
command,
pattern = NULL,
filetype = NULL,
gdal = NULL,
...,
tidy_eval = targets::tar_option_get("tidy_eval"),
packages = targets::tar_option_get("packages"),
library = targets::tar_option_get("library"),
repository = targets::tar_option_get("repository"),
iteration = targets::tar_option_get("iteration"),
error = targets::tar_option_get("error"),
memory = targets::tar_option_get("memory"),
garbage_collection = targets::tar_option_get("garbage_collection"),
deployment = targets::tar_option_get("deployment"),
priority = targets::tar_option_get("priority"),
resources = targets::tar_option_get("resources"),
storage = targets::tar_option_get("storage"),
retrieval = targets::tar_option_get("retrieval"),
cue = targets::tar_option_get("cue")) {
check_pkg_installed("terra")

name <- targets::tar_deparse_language(substitute(name))

envir <- targets::tar_option_get("envir")

command <- targets::tar_tidy_eval(
expr = as.expression(substitute(command)),
envir = envir,
tidy_eval = tidy_eval
)

pattern <- targets::tar_tidy_eval(
expr = as.expression(substitute(pattern)),
envir = envir,
tidy_eval = tidy_eval
)

drv <- get_gdal_available_driver_list("raster")

# if not specified by user, pull the corresponding geotargets option
filetype <- filetype %||% geotargets_option_get("gdal.raster.driver")
filetype <- rlang::arg_match0(filetype, drv$name)

gdal <- gdal %||% geotargets_option_get("gdal.raster.creation_options")

targets::tar_target_raw(
name = name,
command = command,
pattern = pattern,
packages = packages,
library = library,
format = create_format_terra_rasters_sprc(filetype = filetype,
gdal = gdal,
...),
repository = repository,
iteration = iteration,
error = error,
memory = memory,
garbage_collection = garbage_collection,
deployment = deployment,
priority = priority,
resources = resources,
storage = storage,
retrieval = retrieval,
cue = cue
)
}

#' @param filetype File format expressed as GDAL driver names passed to `terra::writeRaster()`
#' @param gdal GDAL driver specific datasource creation options passed to `terra::writeRaster()`
#' @param ... Additional arguments not yet used
#' @noRd
create_format_terra_rasters_sprc <- function(filetype, gdal, ...) {
check_pkg_installed("terra")

drv <- get_gdal_available_driver_list("raster")

filetype <- filetype %||% geotargets_option_get("gdal.raster.driver")
filetype <- rlang::arg_match0(filetype, drv$name)

gdal <- gdal %||% geotargets_option_get("gdal.raster.creation_options")
## TODO
## Need to append the "opt" argument for GDAL options that is currently
## controlled with the if(i > 1) part.

.write_terra_rasters_sprc <- eval(
substitute(
function(object, path) {
for (i in seq(object)) {
if (i > 1) {
opt <- "APPEND_SUBDATASET=YES"
} else {
opt <- ""
}
terra::writeRaster(
x = object[i],
filename = path,
filetype = filetype,
overwrite = (i == 1),
gdal = opt
)
}
},
list(filetype = filetype, gdal = gdal)
)
)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if it might be more useful to pull this out and create a write_sprc() function? Would it work on any SpatRasterCollection outside of a targets pipeline?

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmmm interesting point! I'm not sure.

Copy link
Owner Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure if this is something we should add, in terms of reading/writing function outside of geotargets, we should let the targets manage that work.


format_sprc_geotiff <- targets::tar_format(
read = function(path) terra::sprc(path),
write = .write_terra_rasters_sprc,
marshal = function(object) terra::wrap(object),
unmarshal = function(object) terra::unwrap(object)
)

format_sprc_geotiff
}
Loading
Loading