perf(build-newer-r): skip packages that already have a binary in bulk
Decide the already-built candidates from one listing per slot and one ABI-verdict query instead of a DB connection and several S3 requests per package; anything undecidable still goes through bincraft.
This commit is contained in:
parent
7f6a15abb2
commit
c3e95f7c69
1 changed files with 195 additions and 0 deletions
|
|
@ -27,6 +27,94 @@ message(sprintf(
|
|||
if ("--dry-run" %in% args) {
|
||||
print(pkgs, row.names = FALSE)
|
||||
} else {
|
||||
# Most candidates were built on an earlier run. Asking bincraft about each one
|
||||
# costs a DB connection plus several S3 requests, about 4s a package, so the
|
||||
# loop spent well over an hour per run re-confirming existing binaries.
|
||||
# Decide those in bulk first; bincraft still checks whatever is left.
|
||||
local_machine <- Sys.info()[["machine"]]
|
||||
arch <- if (grepl("arm64|aarch64", local_machine)) "arm64" else "amd64"
|
||||
slot_dir <- sprintf(
|
||||
"devxy-rpkgs-binaries/%s/%s/latest/src/contrib",
|
||||
arch,
|
||||
bincraft::set_codename(NULL)
|
||||
)
|
||||
s3fs::s3_file_system(
|
||||
aws_access_key_id = Sys.getenv("B2_S3_ACCESS_KEY"),
|
||||
aws_secret_access_key = Sys.getenv("B2_S3_SECRET_KEY"),
|
||||
endpoint = "https://s3.eu-central-003.backblazeb2.com",
|
||||
region_name = "eu-central-003",
|
||||
refresh = TRUE
|
||||
)
|
||||
# NULL when the listing fails, so that route falls back to bincraft.
|
||||
list_etags <- function(dir) {
|
||||
info <- tryCatch(s3fs::s3_dir_info(dir), error = function(e) {
|
||||
message(sprintf("Could not list %s: %s", dir, conditionMessage(e)))
|
||||
NULL
|
||||
})
|
||||
if (is.null(info)) {
|
||||
return(NULL)
|
||||
}
|
||||
stats::setNames(
|
||||
gsub('^"|"$', "", as.character(info$etag)),
|
||||
basename(as.character(info$uri))
|
||||
)
|
||||
}
|
||||
# The verdicts bincraft::classify_r_minor_sensitive() would read from its
|
||||
# cache, fetched in one query rather than one connection per package.
|
||||
read_verdicts <- function(packages) {
|
||||
tryCatch(
|
||||
{
|
||||
con <- DBI::dbConnect(
|
||||
RPostgres::Postgres(),
|
||||
dbname = "build_metadata",
|
||||
host = "r-binaries.devxy.io",
|
||||
port = 15432,
|
||||
user = "rpkgs",
|
||||
password = Sys.getenv("PGPASS"),
|
||||
sslmode = "verify-full"
|
||||
)
|
||||
on.exit(DBI::dbDisconnect(con), add = TRUE)
|
||||
rows <- DBI::dbGetQuery(
|
||||
con,
|
||||
paste(
|
||||
"SELECT package, version, r_minor_sensitive FROM abi_classification",
|
||||
"WHERE classifier_sig = $1 AND package = ANY($2::text[])"
|
||||
),
|
||||
params = list(
|
||||
bincraft:::abi_classifier_signature(),
|
||||
paste0("{", paste(packages, collapse = ","), "}")
|
||||
)
|
||||
)
|
||||
stats::setNames(
|
||||
as.logical(rows$r_minor_sensitive),
|
||||
paste(rows$package, rows$version, sep = "_")
|
||||
)
|
||||
},
|
||||
error = function(e) {
|
||||
message(sprintf("Could not read ABI verdicts: %s", conditionMessage(e)))
|
||||
logical()
|
||||
}
|
||||
)
|
||||
}
|
||||
sensitive <- read_verdicts(pkgs$Package)
|
||||
before <- nrow(pkgs)
|
||||
pkgs <- newer_r_outstanding(
|
||||
pkgs,
|
||||
sensitive,
|
||||
list_etags(slot_dir),
|
||||
list_etags(file.path(
|
||||
slot_dir,
|
||||
sub("^(\\d+\\.\\d+).*", "\\1", target_r)
|
||||
)),
|
||||
bincraft:::cran_source_md5()
|
||||
)
|
||||
message(sprintf(
|
||||
"%d of %d already carry a binary at their routed path; %d left for bincraft",
|
||||
before - nrow(pkgs),
|
||||
before,
|
||||
nrow(pkgs)
|
||||
))
|
||||
|
||||
options(crayon.enabled = TRUE, Ncpus = 4, future.globals.onReference = NULL)
|
||||
for (i in seq_len(nrow(pkgs))) {
|
||||
message(sprintf(
|
||||
|
|
|
|||
Loading…
Reference in a new issue