Global R upgrade breaks pre-commit #3206
Description
search you tried in the issue tracker
break class update / 2, second upgrade
describe your issue
R is currently implemented as a second class language, i.e. global interpreter required but packages are bootstrapped by pre-commit in virtual environment with {renv}. R packages are installed for a minor version, e.g. R 4.3 and R is not referenced version-specific on the $PATH usually. Hence, updating R means you have to install all these packages again, otherwise your code just won't work (as R on the $PATH now points to the updated R version). However, pre-commit does not know you just updated R and will fail (unless you already used {renv} to update all required dependencies (e.g. for another project) and have not opted out of the {renv} cache). Currently, the clean solution seems to run pre-commit clean (for all hooks since #2338 got rejected). I wonder if other second class languages have similar characteristics. Can pre-commit recognise that the global R version changed and then just re-install that specific environment or at least give helpful error messages?
Downstream reference: lorenzwalthert/precommit#567
pre-commit --version
pre-commit 3.3.3
.pre-commit-config.yaml
repo: https://github.com/lorenzwalthert/precommit~/.cache/pre-commit/pre-commit.log (if present)
spell-check..............................................................Failed
- hook id: spell-check
- exit code: 1
ℹ Using R 4.4.0 (lockfile was generated with R 4.3.3)
ℹ Using R 4.4.0 (lockfile was generated with R 4.3.3)
Error in loadNamespace(x) : there is no package called ‘precommit’
Calls: loadNamespace -> withRestarts -> withOneRestart -> doWithOneRestart
Execution halted
Activity
asottile commentedon May 20, 2024
the fix for this would be to implement
healthyfor R, similar to how it is done for pythonlorenzwalthert commentedon May 20, 2024
I saw that in
CONTRIBUTING.md... So this would just give an error message and say "run pre-commit clean" or are there interventions with a smaller scope?lorenzwalthert commentedon May 20, 2024
Problem is that the virtual environment is hard to access for the end user, so if pre-commit just ran a
renv::restore(), the problem would be solved I think.lorenzwalthert commentedon May 20, 2024
Also, how to determine the environment is broken? Can we record the R version when the environment is installed and then check it's the same in
healthyor how would you implement such a check?asottile commentedon May 20, 2024
if an environment is unhealthy pre-commit will automatically rebuild it without user intervention
asottile commentedon May 20, 2024
the approach the python one takes is how I'd do it for r
lorenzwalthert commentedon Jul 23, 2024
thanks, I think we can use {renv} APIs to persist the R version in use as a setting in
renv/settings.json, so hence we should be able to detect mismatching R version and implement the health check. While at it, I wondered if we could instead / in addition refactor theLANGUAGE_VERSIONproperty. Currently, we just uselang_base.basic_get_default_version, but could we not make this R version dependent and hence also solve the problem that way or is that an add on after we implemented the health check?