knitr icon indicating copy to clipboard operation
knitr copied to clipboard

Export `parse_params()` for developers of functionality in third-party packages adjacient to {knitr}

Open lorenzwalthert opened this issue 2 years ago • 6 comments

By filing an issue to this repo, I promise that

  • [x] I have fully read the issue guide at https://yihui.org/issue/.
  • [x] I have provided the necessary information about my issue.
    • If I'm asking a question, I have already asked it on Stack Overflow or RStudio Community, waited for at least 24 hours, and included a link to my question there.
    • If I'm filing a bug report, I have included a minimal, self-contained, and reproducible example, and have also included xfun::session_info('knitr'). I have upgraded all my packages to their latest versions (e.g., R, RStudio, and R packages), and also tried the development version: remotes::install_github('yihui/knitr').
    • If I have posted the same issue elsewhere, I have also mentioned it in this issue.
  • [x] I have learned the Github Markdown syntax, and formatted my issue correctly.

I understand that my issue may be closed if I don't fulfill my promises.


I'd ask you to export parse_params() so other projects that are adjacient to {knitr} can leverage that functionality in their developing efforts. This would most likely make the end user experience more consistent and reduce code duplication. In particular, in {styler}, we currently parse the parameters ourself to:

  • Determine if the code chunk is R code and if yes, we format the chunk. This turned out to be more complicated than we thought with multiple edge cases to accout for over the last few years: https://github.com/r-lib/styler/issues/928, https://github.com/r-lib/styler/issues/312, https://github.com/r-lib/styler/issues/831
  • To format the code chunk header itself: https://github.com/r-lib/styler/issues/839

{knitr} already expors some functionality that most end users don't need, like sew(), all_patterns and more, so exporting parse_params() be in line with current API policies. There are most likely other packages that would benefit in the long run, plus the API of that function is probably quite established and stable.

This came up in https://github.com/r-lib/styler/issues/928.

lorenzwalthert avatar Mar 11 '22 09:03 lorenzwalthert

Exporting the current parse_params() is not enough. It could help you if users specify the engine option, but for R Markdown users, the engine is usually specified directly after the three backticks, i.e., ```{Rcpp} instead of ```{r, engine="Rcpp"}.

I'll need to move some code from parse_block().

Anyway, I'm okay with exporting these low-level functions, but probably not very soon.

yihui avatar Mar 24 '22 03:03 yihui

Ok thanks, sounds good 👍

lorenzwalthert avatar Mar 24 '22 06:03 lorenzwalthert

Actually, I feel that exporting parse_params() won't really help you with the two problems. I don't know much about how styler parses knitr documents, but I feel parse_params() is not what you want to use. To make sure, you can start with knitr:::parse_params (triple-colon). If it can solve your problem, I can certainly export it, but I doubt so.

yihui avatar Mar 24 '22 17:03 yihui

Ok, I think I get what you mean now, i.e. if engine is not set it is parsed as a label in my understanding:

knitr:::parse_params("a=1, engine='Rcpp'")
#> $a
#> [1] 1
#> 
#> $engine
#> [1] "Rcpp"
#> 
#> $label
#> [1] "unnamed-chunk-3"

knitr:::parse_params("Rcpp, foo, a=1,")
#> $label
#> [1] "Rcpp, foo"
#> 
#> $a
#> [1] 1

Created on 2022-03-10 by the reprex package (v2.0.1.9000)

Is that the problem you said we'll encounter? Of course, if we can get

knitr:::parse_params("Rcpp, foo, a=1,")
#> $engine
#> [1] "Rcpp"
#> $label
#> [1] "foo"
#> 
#> $a
#> [1] 1

from parse_params(), that would make our life easier. Can we safely assume that if engine is not returned, everything in label up to the first comma is the engine?

lorenzwalthert avatar Jul 26 '22 14:07 lorenzwalthert

If you only work with R Markdown documents, you can preprocess the chunk header before passing it to parse_params():

params = sub('^([a-zA-Z0-9_]+)(.*)$', 'engine="\\1",\\2', params)

Yes, for R Markdown, you can safely assume the first string is always the engine.

yihui avatar Jul 28 '22 22:07 yihui

ok, great. Thanks for the regex. {styler} styles .R, .Rprofile, .Rmd, .Rmarkdown, .qmd and .Rnw and IIRC .Rnw can only contain R code so I think we've got everything covered.

lorenzwalthert avatar Aug 07 '22 15:08 lorenzwalthert

Great! Just a small correction: .Rnw can contain other languages, too (use the chunk option engine).

yihui avatar Aug 11 '22 16:08 yihui

This old thread has been automatically locked. If you think you have found something related to this, please open a new issue by following the issue guide (https://yihui.org/issue/), and link to this old issue if necessary.

github-actions[bot] avatar Feb 15 '23 05:02 github-actions[bot]