Skip to content

Commit

Permalink
Merge pull request #123 from gadenbuie/rc-v1.0.0
Browse files Browse the repository at this point in the history
  • Loading branch information
gadenbuie authored Sep 20, 2023
2 parents 3d79f5b + 78afee0 commit 67da1f7
Show file tree
Hide file tree
Showing 24 changed files with 803 additions and 261 deletions.
2 changes: 1 addition & 1 deletion DESCRIPTION
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
Package: epoxy
Title: String Interpolation for Documents, Reports and Apps
Version: 0.1.1.9000
Version: 1.0.0
Authors@R: c(
person("Garrick", "Aden-Buie", , "[email protected]", role = c("aut", "cre"),
comment = c(ORCID = "0000-0002-7111-0077")),
Expand Down
83 changes: 45 additions & 38 deletions NEWS.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,30 @@
# epoxy (development version)
# epoxy 1.0.0

* `epoxy()` now adds a `.data` pronoun that allows you to refer to the list or
data frame passed into either the `.data` argument of `epoxy()` or the `data`
or `.data` chunk options. (#100)
## Breaking Changes

* **Breaking change:** `epoxy_latex()` and the `epoxy_latex` chunk engine it
powers now use `<<` and `>>` to delimit inline expressions. Where you
previously may have used `<expr>`, please now use `<<expr>>`. This breaking
change was necessary to allow the `expr` to include common R operators like
`<` and `>`. (#107)

* **Breaking change:** the `whisker` engine is now powered by
`epoxy_mustache()`, resulting in a few small changes. In particular, if you
previously used a list for the `.data` chunk option in a `whisker` chunk, and
relied on the `whisker` engine's special treatment of lists to iterate over
their items, you'll need to specifically opt into this behavior by adding a
`.vectorized = TRUE` chunk option.

This chunk engine still vectorizes over rows in a data frame by default, where
it's much more likely to be the behavior you want, but bare lists require
specifically opting in. (#103)

* `.data` is now the preferred chunk option for passing data frames or lists of
data to epoxy chunks. It works in `whisker` and `epoxy` chunks, and is more
consistent with the `.data` argument of `glue()` and `epoxy()`. (#102)
data to epoxy chunks, where previously `data` was used in some places. It
works in `whisker` and `epoxy` chunks, and is more consistent with the `.data`
argument of `glue()` and `epoxy()`. (#102)

## New Features

* New `epoxy_mustache()` provides an epoxy-style interface to the
[mustache](https://mustache.github.io/) templating language, using the
Expand All @@ -19,26 +37,29 @@
`epoxy()`, `epoxy_html()` or other epoxy-provided knitr chunk or file as a
template. `epoxy_use_chunk()` lets you re-use a template chunk with new data,
and `epoxy_use_file()` lets you repeatedly use a template stored in a file.
Both function also re-use the options from the template chunk or the options
Both functions also re-use the options from the template chunk or the options
set in the YAML from matter of the template file. See `?epoxy_use` for more
details about how options for both functions are determined. (#106, #116)

* **Breaking change:** now that the `whisker` engine is powered by
`epoxy_mustache()`, there have been a few small changes. In particular, if you
previously used a list for the `.data` chunk option in a `whisker` chunk, and
relied on the `whisker` engine's special treatment of lists to iterate over
their items, you'll need to specifically opt into this behavior by adding a
`.vectorized = TRUE` chunk option.
## Improvements and bug fixes

This chunk engine still vectorizes over rows in a data frame by default, where
it's much more likely to be the behavior you want, but bare lists require
specifically opting in. (#103)
* `epoxy()` now adds a `.data` pronoun that allows you to refer to the list or
data frame passed into either the `.data` argument of `epoxy()` or the `data`
or `.data` chunk options. (#100)

* **Breaking change:** `epoxy_latex()` and the `epoxy_latex` chunk engine it
powers now use `<<` and `>>` to delimit inline expressions. Where you
previously may have used `<expr>`, please now use `<<expr>>`. This breaking
change was necessary to allow the `expr` to include common R operators like
`<` and `>`. (#107)
* `epoxy_html()` now supports inline transformations prefixed with `@` instead
of `.`, e.g. `@strong` instead of `.strong`. Previously, you would have to
place the inline transformer in a nested `{{ }}` block, e.g.
`{{ {{ .strong expr }} }}`, but now you only need `{{@strong expr}}`. To combine the HTML transformer (`epoxy_transform_html()`) with the inline
transformer, you still need to nest: `{{.text-muted {{@strong expr}}}}`
creates `<span class="text-muted"><strong>{expr}</strong></span>`. (#120)

* `epoxy()`, and by extension the LaTex and HTML counterparts, and all `epoxy_*`
knitr engines gain a `.collapse` argument to determine how a vector of
epoxy-transformed templates should be collapsed. The default is `NULL`, which
means that the output is returned as a vector. This argument is also useful in
`epoxy_use_chunk()` and for knitr chunks being used as a vectorized template.
(#115)

* Aded `.sentence` (alias `.sc`) to the list of inline transformers provided by
`epoxy_transform_inline()`. This transformer will capitalize the first letter
Expand All @@ -49,27 +70,13 @@
`as.character()` before applying `tools::toTitleCase()`, since `toTitleCase()`
will throw an error for non-character inputs. (#112)

* `epoxy()`, and by extension the LaTex and HTML counterparts, and all `epoxy_*`
knitr engines gain a `.collapse` argument to determine how a vector of
epoxy-transformed templates should be collapsed. The default is `NULL`, which
means that the output is returned as a vector. This argument is also useful in
`epoxy_use_chunk()` and for knitr chunks being used as a vectorized template.
(#115)

* Fixed an issue with `epoxy_inline_transform()` when used with custom
delimiters (#116).

* `epoxy()`, `epoxy_html()`, `epoxy_latex()` and `epoxy_mustache()` (and their
related knitr engines) will all collect remote `tbl_sql` tables before
evaluation. This makes it much easier to pass data from a remote database
using `{dplyr}` and `{dbplyr}`. (#117)

* `epoxy_html()` now supports inline transformations prefixed with `@` instead
of `.`, e.g. `@strong` instead of `.strong`. Previously, you would have to
place the inline transformer in a nested `{{ }}` block, e.g.
`{{ {{ .strong expr }} }}`, but now you only need `{{@strong expr}}`. To combine the HTML transformer (`epoxy_transform_html()`) with the inline
transformer, you still need to nest: `{{.text-muted {{@strong expr}}}}`
creates `<span class="text-muted"><strong>{expr}</strong></span>`. (#120)
* Fixed an issue with `epoxy_inline_transform()` when used with custom
delimiters (#116).

# epoxy 0.1.1

Expand Down Expand Up @@ -211,7 +218,7 @@ versions that were available on GitHub prior to the CRAN release.
(#37).

* `epoxy_transform_collapse()` now uses the
[and package](https://and.rossellhayes.com/), which provides language-aware
[and package](https://github.com/rossellhayes/and/), which provides language-aware
conjoining of strings. As a result, the `sep_and` and `sep_or` arguments of
`epoxy_transform_collapse()` are deprecated and are silently ignored if
provided (#45).
Expand Down
32 changes: 23 additions & 9 deletions R/epoxy_use.R
Original file line number Diff line number Diff line change
Expand Up @@ -111,8 +111,7 @@ epoxy_use_chunk <- function(.data = NULL, label, ...) {
template$code,
.data = .data,
...,
options = template$opts,
engine = template$opts$engine
options = template$opts
)
}

Expand All @@ -135,19 +134,24 @@ epoxy_use_file <- function(.data = NULL, file, ...) {
template,
.data = .data,
...,
options = options,
engine = options$engine %||% "epoxy"
options = options
)
}

read_body_without_yaml <- function(path) {
x <- readLines(path)
x_trimmed <- trimws(x)

if (!any(nzchar(x_trimmed))) {
rlang::abort(paste0("File '", path, "' is empty"))
}

idx_nzchar <- which(nzchar(x_trimmed))[1]
idx_start <- grep("^---$", x_trimmed)[1]
idx_start <- grep("^---$", x_trimmed)

if (idx_nzchar < idx_start) {
if (length(idx_start)) idx_start <- idx_start[1]

if (length(idx_start) == 0 || idx_nzchar < idx_start) {
return(paste(x, collapse = "\n"))
}

Expand All @@ -170,7 +174,7 @@ epoxy_use_template <- function(
.data = NULL,
...,
options = list(),
engine = options$engine
engine = NULL
) {
# For options, we want to apply options in this order:
# 0. `.data` from this fn and `eval` from this chunk
Expand All @@ -190,17 +194,27 @@ epoxy_use_template <- function(
opts <- purrr::list_assign(opts, !!!opts_current)
opts <- purrr::list_assign(opts, !!!purrr::compact(opts_fn))

engine <- engine %||% options$engine %||% "epoxy"

fn <- switch(
engine,
epoxy = epoxy,
html = ,
epoxy_html = epoxy_html,
latex = ,
epoxy_latex = epoxy_latex,
mustache = epoxy_mustache,
mustache = ,
whisker = epoxy_mustache,
glue = epoxy,
glue_html = epoxy_html,
glue_latex = epoxy_latex,
epoxy
{
rlang::warn(c(
glue("Unexpected engine '{engine}', defaulting to `epoxy()`."),
"i" = "Set an epoxy knitr engine in the chunk or file."
))
epoxy
}
)

call <- rlang::call2(
Expand Down
Loading

0 comments on commit 67da1f7

Please sign in to comment.