impuresrcref imputes transparent srcref metadata for injected brace calls ({) in R function ASTs.
In R, a srcref is source-location metadata (line/column ranges) attached to
parsed objects when source retention is enabled (for example with
options(keep.source = TRUE)).
This package solves a finer-grained mapping problem for control-flow
expressions written without braces (for example if (x) f() else g()). It
adds transparent wrappers and imputes srcrefs from parse data so individual
control-flow components can be mapped to source precisely.
It uses the parser token tables getParseData for it.
Given code like:
if (x && y) f() else g()impute_srcrefs() rewrites control-flow positions to:
if ({x} && {y}) {f()} else {g()}and assigns srcrefs to injected { calls using parse-data-derived source spans.
impute_srcrefs(fn)- Impute missing control-flow braces and transparent srcrefs for one function.
source_impute_srcrefs(file, envir = parent.frame(), ...)- Source an R file and patch all changed/new functions in the target environment.
impute_package_srcrefs(package, include_internal = TRUE, ...)- Patch package namespace functions if parse data is available
For installed packages, parse data is often missing unless the package was installed from source with source/parse retention enabled.
Recommended installation pattern:
install.packages("<package>", INSTALL_opts=c("--with-keep.source", "--with-keep.parse.data"))options(keep.source = TRUE)
f <- eval(parse(text = "function(x, y) if (x && y) f() else g()", keep.source = TRUE)[[1]])
g <- impute_srcrefs(f)
genv <- new.env(parent = baseenv())
res <- source_impute_srcrefs("path/to/file.R", envir = env)
res$functionsres <- impute_package_srcrefs("stringr", include_internal = TRUE)
res$patched_count
head(res$failed[!is.na(res$failed)])Returned fields are:
packagefn_namesfailed(NAmeans successfully patched)patched_countinstall_command(reinstall hint when nothing could be patched)
impute_srcrefs() requires function srcref metadata by default.
For functions created without srcrefs, opt into deparse-based fallback explicitly:
options(impuresrcref.allow_deparse_fallback = TRUE)Snapshot tests compare generated output against committed .out golden files.
They include regression coverage for:
- package-style
srcrefline mappings (sr[7:8]vssr[1:3]) - zero-formals functions (
function()) Run tests in compare mode:
Rscript tests/test-srcref-imputation.RRefresh snapshots:
UPDATE_SNAPSHOTS=1 Rscript tests/test-srcref-imputation.RBy default, mismatches fail. With UPDATE_SNAPSHOTS=1, the snapshot file is rewritten.
Legacy --update is still accepted for compatibility.
This package was inspired in part by covr's parse-data handling approach.