Defines functions exportFiles exportFiles.redcapDbConnection exportFiles.redcapApiConnection

Documented in exportFiles exportFiles.redcapApiConnection exportFiles.redcapDbConnection

#' @name exportFiles
#' @title Exports a File attached to a Record
#' @description A single file from a single record is retrieved.  The behavior 
#' of this function is consistent with the behavior of the API, which only 
#' allows one file to be downloaded at a time
#' @param rcon A REDCap connection object as generated by \code{redcapConnection}
#' @param record The record ID in which the desired file is stored. Must be length 1.
#' @param field The field name in which the file is stored. Must be length 1. 
#' @param event The event name for the file.  Must be length 1.  
#'   This applies only to longitudinal projects.  If the event is not
#'   supplied for a longitudinal project, the API will return an error message
#' @param dir A directory/folder to which the file will be saved. 
#'   By default, the working directory is used
#' @param filePrefix Logical.  Determines if a prefix is appended to the file 
#'   name.  The prefix takes the form [record_id]-[event_name]-[file_name].  
#'   The file name is always the same name of the file as it exists in REDCap
#' @param ... Arguments to be passed to other methods
#' @param bundle A \code{redcapBundle} object as created by \code{exportBundle}.
#' @param error_handling An option for how to handle errors returned by the API.
#'   see \code{\link{redcap_error}}
#' @details The function may only export a single file.  
#' See the examples for suggestions on exporting multiple files.
#' Note that the name of the file can not be changed.  Whatever name exists in 
#' REDCap is the name that will be used, although the record ID and event name 
#' may be appended as a prefix
#' @section REDCap API Documentation (6.5.0):
#' This method allows you to download a document that has been attached to an 
#' individual record for a File Upload field. Please note that this method may also 
#' be used for Signature fields (i.e. File Upload fields with "signature" validation type).
#' Note about export rights: Please be aware that Data Export user rights will be 
#' applied to this API request. For example, if you have "No Access" data export rights 
#' in the project, then the API file export will fail and return an error. And if you 
#' have "De-Identified" or "Remove all tagged Identifier fields" data export rights, 
#' then the API file export will fail and return an error *only if* the File Upload 
#' field has been tagged as an Identifier field. To make sure that your API request 
#' does not return an error, you should have "Full Data Set" export rights in the project.
#' @section REDCap Version:
#' 5.8.2+ 
#' @section Known REDCap Limitations:
#' None
#' @author Benjamin Nutter
#' @references
#' Please refer to your institution's API documentation.
#' Additional details on API parameters are found on the package wiki at
#' \url{https://github.com/nutterb/redcapAPI/wiki/REDCap-API-Parameters}
#' @export

exportFiles <- function(rcon, record, field, event, dir, filePrefix=TRUE, ...,
                        bundle = getOption("redcap_bundle"))

#' @rdname exportFiles
#' @export

exportFiles.redcapDbConnection <- function(rcon, record, field, event, dir, filePrefix=TRUE, ..., 
                                           bundle = getOption("redcap_bundle")){
  message("Please accept my apologies.  The exportFiles method for redcapDbConnection objects\n",
          "has not yet been written.  Please consider using the API.")

#' @rdname exportFiles
#' @export

exportFiles.redcapApiConnection <- function(rcon, record, field, event = NULL, 
                                            filePrefix=TRUE, ...,
                                            bundle = getOption("redcap_bundle"),
                                            error_handling = getOption("redcap_error_handling")){
  if (!is.na(match("proj", names(list(...)))))
    message("The 'proj' argument is deprecated.  Please use 'bundle' instead")
    bundle <- list(...)[["proj"]]

  if (is.numeric(record)) record <- as.character(record)
  #* Error Collection Object
  coll <- checkmate::makeAssertCollection()
  massert(~ rcon + bundle,
          fun = checkmate::assert_class,
          classes = list(rcon = "redcapApiConnection",
                         bundle = "redcapBundle"),
          null.ok = list(rcon = FALSE,
                         bundle = TRUE),
          fixed = list(add = coll))
  massert(~ record + field + event,
          fun = checkmate::assert_character,
          null.ok = list(record = FALSE,
                         field = FALSE,
                         event = TRUE),
          fixed = list(len = 1,
                       add = coll))
  if (missing(dir)){
    coll$push("'dir' must have a character(1) value")
    checkmate::assert_character(x = dir,
                                len = 1, 
                                add = coll)
    if (is.character(dir)){
      if (!dir.exists(dir)){
        coll$push("'dir' is not an existing directory")
  checkmate::assert_logical(x = filePrefix,
                            len = 1,
                            add = coll)
  #* Secure the meta_data
  meta_data <- 
    if (is.null(bundle$meta_data)) 
  #* make sure 'field' exist in the project and are 'file' fields
  if (!field %in% meta_data$field_name) 
    coll$push(paste("'", field, "' does not exist in the project.", sep=""))
  else if (meta_data$field_type[meta_data$field_name == field] != "file")
    coll$push(paste0("'", field, "' is not of field type 'file'"))
  #* Secure the events list
  events_list <- 
    if (is.null(bundle$events))
  #* make sure 'event' exists in the project
  if (inherits(events_list, "data.frame"))
    if (!event %in% events_list$unique_event_name) 
      coll$push(paste0("'", event, "' is not a valid event name in this project."))
  body <- list(token = rcon$token, 
               content = 'file',
               action = 'export', 
               returnFormat = 'csv',
               record = record,
               field = field)
  if (!is.null(event)) body[['event']] <- event
  #* Export the file
  x <- httr::POST(url = rcon$url, 
                  body = body, 
                  config = rcon$config)

  if (x$status_code != 200) redcap_error(x, error_handling)
  #* strip the returned character string to just the file name.
  filename <- sub(pattern = "[[:print:]]+; name=", 
                 replacement = "", 
                 x = x$headers$'content-type')
  filename <- gsub(pattern = "\"", 
                   replacement = "", 
  filename <- sub(pattern = ";charset[[:print:]]+", 
                  replacement = "", 
                  x = filename)
  #* Add the prefix
  if (filePrefix) filename <- paste(record, "-", event, "-", filename, sep="")
  #* Write to a file
  writeBin(object = as.vector(x$content), 
           con = file.path(dir, filename), 
  message("The file was saved to '", filename, "'")


Try the redcapAPI package in your browser

Any scripts or data that you put into this service are public.

redcapAPI documentation built on Feb. 18, 2020, 1:09 a.m.