knitr::opts_chunk$set( results = "asis", echo = FALSE, comment = FALSE, warning = FALSE, message = FALSE, fig.align = "center" ) library(nomnoml)
Supplementary utils for CRAN maintainers and R package developers in the pacs package. The wide range of tools to achieve healthy R environment and make the R developer life easier. Each of the function was inspired be everyday challenges which have to be faced by the experienced R developer in the production quality agile project. These tools should be universal in different work environments.
Docker
/Podman
, a full reproducibility.renv
, a python pip in the R world. Helps manage the R packages used in a project; it (at least not yet) does not provide any tools for associating a particular version of R with a project. The R community tinyverse
movement is a tryout to create a new package development standards. The clue is the TINY part here.
The last years of R package development were full of high number of dependencies temptations.
tinyverse
means as least dependencies as possible as R package dependencies matter.
Every dependency you add to your project is an invitation to break your project.
More information is available in the tinyverse
vignette.
Minimize dependencies and avoid installing "nice to have" packages.
The objective should be to have zero dependencies in an R package.
That is why tinytest
was created or renv
has zero dependencies.
Check a package dependencies exposed to the end users with pacs::pac_deps_user
, these are packages installed with the install.packages
.
When adding a package to Depends, Imports or LinkingTo, then we impact end users when they invoke install.packages
. On the other hand if a package is added to Suggests, this impacts mainly developers e.g. R CMD CHECK
, check all developer exposed packages with pacs::pac_deps_dev
.
The main strategy should be to prefer usage of pacs::pacs_base()
packages (already installed in R) and packages with only a few dependencies (the best zero like jsonlite
).
One method of reducing number of dependencies (exposed to end users) is to transfer the package from Imports to Suggests and load it in the delayed manner, or not include it at all.
Check the tinyverse
vignette for more details.
func <- function() { if (requireNamespace("PACKAGE", quietly = TRUE)) { # regular code } else { stop("Please install the PACKAGE to use the func function") } }
Important topics to consider to have a secure, light and healthy library.
We should be careful when adding/updating packages.
The updating part could be surprising nevertheless e.g. in bigger projects we want to have a stable library for each product release.
Tools: pacs
, remotes
, CRAN packages websites, cranlogs, and repository website like github.
Example: We think of adding/updating the parsnip
package.
```{nomnoml, fig.width=16, fig.height=9, svg=FALSE}
[Add a Package| [YAGNI]-[Add a Package] [LIFE DURATION] - [Add a Package] [CRAN CHECK PAGE] - [Add a Package] [VERSION]-[Add a Package] [Add a Package]-[NEW DEPENDENCIES] [Add a Package]-[REPO ACTIVITY] [Add a Package]-[COVR] [Add a Package]-[DOWNLOADS] ]
```{nomnoml, fig.width=16, fig.height=8, svg=FALSE} #stroke: black #padding: 0 #spacing: 0 #fontSize: 12 #.box: [<frame>Update a Package| [YAGNI]-[Update a Package] [LIFE DURATION]-[Update a Package] [CRAN CHECK PAGE]-[Update a Package] [Update a Package]-[NEW DEPENDENCIES] [Update a Package]-[NEWS] [Update a Package]-[SCOPE] ]
pacs::pac_checkpage("parsnip")
.pacs::pac_timemachine("parsnip")
or pacs::pac_lifeduration("parsnip")
.remotes::package_deps("parsnip")
.utils::news(package = "parsnip")
; CRAN NEWS PAGEpacs::pac_compare_versions("parsnip")
and pacs::pac_compare_namespace("parsnip")
.pacs::pac_description("parsnip")
or pacs::pac_last("parsnip")
.We could validate numerous things like: R library, R package or renv
lock file.
Even if we will not find any obvious problems we will need a proof that the environment is validated which is often the authorities' requirement.
R library could be easily broken with functions like remotes::install_version
or remotes::install_github(..., dependencies = FALSE)
. On the other hand the renv
lock file could be built manually or by an external automation pipeline.
We could control many risks with pacs::lib_validate
, pacs::pac_validate
and pacs::lock_validate
functions.
```{nomnoml, fig.width=16, fig.height=6, svg=FALSE}
[Validate| [VERSIONS]-[Validate] [CRAN CHECK PAGES]-[Validate] [Validate]-[Built] [Validate]-[LIFE DURATIONS] [Validate]-[NEWEST] ]
- **LIFE DURATIONS**, life duration of the version where we should expected at least 14 days. - **VERSIONS**, do we have the same versions as required by DESCRIPTION files. - **NEWEST**, is the newest version. - **BUILT**, packages installed with a previous version of R could not work correctly with the new version of R. Mostly for local usage (without `renv`) and a minor (last number) R version update. - **CRAN CHECK PAGE**, CRAN checks on variety of servers. We could extract checks for all CRAN packages with `pacs::checked_packages()`. - **OTHER** ```r # assesing life durations could be time consuming for a bigger library. pacs::lib_validate( checkred = list( scope = c("ERROR", "FAIL"), flavors = pacs::cran_flavors()$Flavor ), lifeduration = FALSE )
Think tiny
and be minimalist for better UX and easier development work.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.