From dae117f3d94d6c49873e6759b4da1b0a8bd7ea0e Mon Sep 17 00:00:00 2001 From: James Lamb Date: Fri, 7 Feb 2025 22:07:49 -0600 Subject: [PATCH] make install-r-deps more flexible --- .ci/install-r-deps.R | 83 +++++++++++++++++++++------ .ci/test-r-package-windows.ps1 | 2 +- .ci/test-r-package.sh | 2 +- .github/workflows/r_package.yml | 2 +- .github/workflows/static_analysis.yml | 2 +- .vsts-ci.yml | 4 +- 6 files changed, 71 insertions(+), 24 deletions(-) diff --git a/.ci/install-r-deps.R b/.ci/install-r-deps.R index a4fe94cfd425..586cf89eee34 100644 --- a/.ci/install-r-deps.R +++ b/.ci/install-r-deps.R @@ -1,10 +1,60 @@ -args <- commandArgs(trailingOnly = TRUE) +# install R dependencies, using only base R +# +# Supported arguments: +# +# --all Install all the 'Depends', 'Imports', 'LinkingTo', and 'Suggests' dependencies. +# (automatically implies --build --test). +# +# --build install the packages needed to build +# +# --exclude= Comma-delimited list of packages to NOT install. +# +# --include= Comma-delimited list of additional packages to install. +# These will always be installed, unless also used in "--exclude". +# +# --test install packages needed to run tests +# + + +# [description] Parse command line arguments into an R list. +# Returns a list where keys are arguments and values +# are either TRUE (for flags) or a vector of values passed via a +# comma-delimited list. +.parse_args <- function(args) { + out <- list( + "--all" = FALSE + , "--build" = FALSE + , "--exclude" = character(0L) + , "--include" = character(0L) + , "--test" = FALSE + ) + for (arg in args) { + print(sprintf("arg: '%s'", arg)) + parsed_arg <- unlist(strsplit(arg, "=", fixed = TRUE)) + arg_name <- parsed_arg[[1L]] + if (!(arg_name %in% names(out))) { + stop(sprintf("Unrecognized argument: '%s'", arg_name)) + } + if (length(parsed_arg) == 2L) { + # lists, like "--include=roxygen2,testthat" + values <- unlist(strsplit(parsed_arg[[2L]], ",", fixed = TRUE)) + out[[arg_name]] <- values + } else { + # flags, like "--build" + out[[arg]] <- TRUE + } + } + return(out) +} + +args <- .parse_args( + commandArgs(trailingOnly = TRUE) +) # which dependencies to install -ALL_DEPS <- "--all" %in% args -BUILD_DEPS <- ALL_DEPS || ("--build" %in% args) -ROXYGEN_DEPS <- ALL_DEPS || ("--roxygen" %in% args) -TEST_DEPS <- ALL_DEPS || ("--test" %in% args) +ALL_DEPS <- isTRUE(args[["--all"]]) +BUILD_DEPS <- ALL_DEPS || isTRUE(args[["--build"]]) +TEST_DEPS <- ALL_DEPS || isTRUE(args[["--test"]]) # force downloading of binary packages on macOS COMPILE_FROM_SOURCE <- "both" @@ -40,13 +90,6 @@ if (isTRUE(BUILD_DEPS)) { ) } -if (isTRUE(ROXYGEN_DEPS)) { - deps_to_install <- c( - deps_to_install - , "roxygen" - ) -} - if (isTRUE(TEST_DEPS)) { deps_to_install <- c( deps_to_install @@ -55,11 +98,17 @@ if (isTRUE(TEST_DEPS)) { ) } -# in some builds, {Matrix} is pre-installed to pin to an old version, -# so we don't want to overwrite that -if (requireNamespace("Matrix")) { - deps_to_install <- setdiff(deps_to_install, "Matrix") -} +# add packages passed through '--include' +deps_to_install <- unique(c( + deps_to_install + , args[["--include"]] +)) + +# remove packages passed through '--exclude' +deps_to_install <- setdiff( + x = deps_to_install + , args[["--exclude"]] +) msg <- sprintf( "[install-r-deps] installing R packages: %s\n" diff --git a/.ci/test-r-package-windows.ps1 b/.ci/test-r-package-windows.ps1 index 9c95d06e028a..a10c056472b2 100644 --- a/.ci/test-r-package-windows.ps1 +++ b/.ci/test-r-package-windows.ps1 @@ -176,7 +176,7 @@ Remove-Item "$env:RTOOLS_MINGW_BIN/cmake.exe" -Force -ErrorAction Ignore Write-Output "Done installing CMake" Write-Output "Installing dependencies" -Rscript.exe --vanilla ".ci/install-r-deps.R" --build --test ; Assert-Output $? +Rscript.exe --vanilla ".ci/install-r-deps.R" --build --include=processx --test ; Assert-Output $? Write-Output "Building R-package" diff --git a/.ci/test-r-package.sh b/.ci/test-r-package.sh index 1837b752aa32..b0ec78ad2918 100755 --- a/.ci/test-r-package.sh +++ b/.ci/test-r-package.sh @@ -113,7 +113,7 @@ Rscript --vanilla -e "install.packages('lattice', repos = '${CRAN_MIRROR}', lib Rscript --vanilla -e "install.packages('https://cran.r-project.org/src/contrib/Archive/Matrix/Matrix_1.6-5.tar.gz', repos = NULL, lib = '${R_LIB_PATH}')" # Manually install dependencies to avoid a CI-time dependency on devtools (for devtools::install_deps()) -Rscript --vanilla ./.ci/install-r-deps.R --build --test || exit 1 +Rscript --vanilla ./.ci/install-r-deps.R --build --test --exclude=Matrix || exit 1 cd "${BUILD_DIRECTORY}" PKG_TARBALL="lightgbm_$(head -1 VERSION.txt).tar.gz" diff --git a/.github/workflows/r_package.yml b/.github/workflows/r_package.yml index 40493f94266a..df4507e8da2b 100644 --- a/.github/workflows/r_package.yml +++ b/.github/workflows/r_package.yml @@ -310,7 +310,7 @@ jobs: - name: Install packages and run tests shell: bash run: | - Rscript ./.ci/install-r-deps.R --build --test + Rscript ./.ci/install-r-deps.R --build --test --exclude=testthat sh build-cran-package.sh # 'rchk' isn't run through 'R CMD check', use the approach documented at diff --git a/.github/workflows/static_analysis.yml b/.github/workflows/static_analysis.yml index 7bc4ff45a835..57b02bc1e4db 100644 --- a/.github/workflows/static_analysis.yml +++ b/.github/workflows/static_analysis.yml @@ -64,7 +64,7 @@ jobs: - name: Install packages shell: bash run: | - Rscript ./.ci/install-r-deps.R --build --roxygen + Rscript ./.ci/install-r-deps.R --build --include=roxygen sh build-cran-package.sh || exit 1 R CMD INSTALL --with-keep.source lightgbm_*.tar.gz || exit 1 - name: Test documentation diff --git a/.vsts-ci.yml b/.vsts-ci.yml index b57aada381d0..0f44f4d4365e 100644 --- a/.vsts-ci.yml +++ b/.vsts-ci.yml @@ -414,16 +414,14 @@ jobs: - script: | git clean -d -f -x displayName: 'Clean source directory' - # yamllint disable rule:line-length - script: | LGB_VER=$(head -n 1 VERSION.txt | sed "s/rc/-/g") R_LIB_PATH=~/Rlib export R_LIBS=${R_LIB_PATH} mkdir -p ${R_LIB_PATH} - RDscript .ci/install-r-deps.R --build --test || exit 1 + RDscript .ci/install-r-deps.R --build --include=RhpcBLASctl || exit 1 sh build-cran-package.sh --r-executable=RD || exit 1 mv lightgbm_${LGB_VER}.tar.gz $(Build.ArtifactStagingDirectory)/lightgbm-${LGB_VER}-r-cran.tar.gz - # yamllint enable rule:line-length displayName: 'Build CRAN R-package' - task: PublishBuildArtifacts@1 condition: succeeded()