The headline call: runs the xportr pipeline (type, length, label, format, order, then write) for every dataset in spec, lays the results out as a submission folder of .xpt transport files, splits any file over split_mb into the conventionally numbered parts (name1.xpt, name2.xpt, ...), and returns the manifest of what was written.

write_submission(
  data,
  spec,
  path,
  split_mb = NULL,
  max_file_mb = 5000,
  define_xml = NULL
)

Arguments

data

A named list of data frames, one per dataset, named to match spec$datasets$dataset.

spec

A submission_spec() object.

path

Output directory for the submission folder (created if needed).

split_mb

Optional. If a written transport file would exceed this many megabytes, it is split into multiple parts via xportr::xportr_write(max_size_gb = ). NULL (default) never splits. Parts written this way are consistent by construction, since they come from one data frame; to check parts you did not write here, pass their paths to check_submission().

max_file_mb

Per-file size ceiling in megabytes, passed to check_submission(). See there for what it defaults to and why.

define_xml

Optional Define-XML hook. Either a path to an existing Define-XML file to copy alongside the transport files, or a function function(spec, path) called after the datasets are written (e.g. to generate one). NULL (default) does nothing.

Value

A submission_manifest tibble (see submission_manifest()), invisibly.

Details

Before writing anything, check_submission() is run; any "error" severity violation aborts the write (aggregated into one message) so a submission that would be rejected never reaches disk. "warning" severity violations (e.g. non-ASCII characters) are reported but do not block the write. Read ?check_submission for the full list of what is and is not checked — it is a transport-layer gate, not a conformance engine.

Define-XML

submitpack does not generate Define-XML. define_xml is a hook: give it the path of a Define-XML file you already have and it is copied into the folder, or give it a function(spec, path) and it is called after the transport files are written, with the spec and the output directory. The define21 package's write_define() fits that signature; so does a call out to any other generator. Nothing about the hook is validated beyond it being a readable path or a function — if your generator writes nothing, submitpack will not notice.

Examples

datasets <- data.frame(dataset = "DM", label = "Demographics", class = "SDTM")
variables <- data.frame(
  dataset = "DM",
  variable = c("USUBJID", "AGE", "SEX"),
  label = c("Unique Subject Identifier", "Age", "Sex"),
  type = c("character", "numeric", "character"),
  length = c(20, 8, 1),
  format = NA_character_,
  order = 1:3
)
spec <- submission_spec(datasets, variables)
dm <- data.frame(
  USUBJID = c("CDISC-001", "CDISC-002"),
  AGE = c(63, 35),
  SEX = c("M", "F")
)
out <- file.path(tempdir(), "submitpack-demo")
man <- write_submission(list(DM = dm), spec, path = out)
#> 
#> ── All variables in dataset are found in `metadata` ──
#> 
#> ── All variables in dataset are ordered ──
#> 
#>  Wrote DM (2 record(s), 3 variable(s))
#>  Submission written to /tmp/RtmpZEJqch/submitpack-demo  (1 file(s))
man
#> 
#> ── submitpack manifest ─────────────────────────────────────────────────────────
#>  1 file(s) in /tmp/RtmpZEJqch/submitpack-demo  |  1,280 bytes total
#> # A tibble: 1 × 5
#>   file   size_bytes checksum                         records variables
#>   <chr>       <dbl> <chr>                              <int>     <int>
#> 1 dm.xpt       1280 2acc2097bf8af0d9a54e55a4cde10bc7       2         3