Changes dependency installation to use two different CRAN sources: Most packages continue to come from a fixed-date snapshot the same age as the R version (same as before this PR), but now will consult a newer CRAN mirror for packages that both:
specify a minimum version in the DESCRIPTION file of at least one package that depends on them (e.g. Imports: lubridate (>= 1.7.0)), and
the version available in the fixed-date CRAN snapshot is too old to meet the stated minimum.
Motivation and Context
Our Docker images inherit the CRAN settings of the Rocker images we build them from, which all use static snapshots that match the age of the version of R they are built for. This is usually what we want -- someone running an old version of R is likely also running old versions of at least some packages, so it makes sense to test PEcAn on a range of dependency versions as well as R versions.
But there are cases where we really do need a functionality or bugfix that is only available in a version of a dependency that was released later than the oldest CRAN snapshot we want to test against. Until now, we've handled this by installing these dependencies from GitHub, usually pinning them to the oldest version known to work. This increases build time (install_github is always from source whereas the Posit package manager gives us prebuilt binaries), creates confusion when the version we pinned goes out of date ("why are we installing this old version of rmarkdown from GitHub instead of using the one on CRAN?"), and generally feels silly.
The change I make here is to take advantage of a nice difference in behavior of remotes::install_version compared to base::install.packages: If argument repos has length > 1, install.packages checks all repositories and installs the newest available version of a package, while install_version checks them in order and installs the first one that matches your version requirements. By looking first in the fixed snapshot and then in the current version of CRAN, we can get several nice properties:
If a dependency is declared with no version limits, we always use the version that was current when the version of R under test was current.
Old R versions always use old versions of packages unless there's an explicit dependency chain requiring them to be updated.
Once a package is updated, we update straight to the current latest version, which matches well with the likely behavior of users trying to update their own machines.
If we discover a limit that needs to be imposed ("that bug was fixed in dbplyr 2.4.0"), declaring the version in DESCRIPTION is enough to impose the limit; the Docker image and therefore the entire CI machinery will pick it up from there.
Declaring a minimum supported version doesn't require downgrading the version installed on newer R releases that were already nwer than the minimum.
Review Time Estimate
[ ] Immediately
[ ] Within one week
[ ] When possible
Types of changes
[ ] Bug fix (non-breaking change which fixes an issue)
[ ] New feature (non-breaking change which adds functionality)
[ ] Breaking change (fix or feature that would cause existing functionality to change)
Checklist:
[ ] My change requires a change to the documentation.
Description
Changes dependency installation to use two different CRAN sources: Most packages continue to come from a fixed-date snapshot the same age as the R version (same as before this PR), but now will consult a newer CRAN mirror for packages that both:
Imports: lubridate (>= 1.7.0)
), andMotivation and Context
Our Docker images inherit the CRAN settings of the Rocker images we build them from, which all use static snapshots that match the age of the version of R they are built for. This is usually what we want -- someone running an old version of R is likely also running old versions of at least some packages, so it makes sense to test PEcAn on a range of dependency versions as well as R versions.
But there are cases where we really do need a functionality or bugfix that is only available in a version of a dependency that was released later than the oldest CRAN snapshot we want to test against. Until now, we've handled this by installing these dependencies from GitHub, usually pinning them to the oldest version known to work. This increases build time (install_github is always from source whereas the Posit package manager gives us prebuilt binaries), creates confusion when the version we pinned goes out of date ("why are we installing this old version of rmarkdown from GitHub instead of using the one on CRAN?"), and generally feels silly.
The change I make here is to take advantage of a nice difference in behavior of
remotes::install_version
compared tobase::install.packages
: If argumentrepos
has length > 1,install.packages
checks all repositories and installs the newest available version of a package, whileinstall_version
checks them in order and installs the first one that matches your version requirements. By looking first in the fixed snapshot and then in the current version of CRAN, we can get several nice properties:Review Time Estimate
Types of changes
Checklist: