Skip to content

Commit cd9f03e

Browse files
committed
Vectorize installed package listing
Address review feedback: collapse pak/base/renv into a single .ps.pkg_list_installed() that always uses utils::installed.packages(), scoped by lib.loc for the renv method. The pak::lib_status() branch went away since pak's value is in install/update, not listing. Replace the per-row lapply with vectorized whitespace/email scrubbing and a single Map() to assemble the per-package lists.
1 parent aeb17f7 commit cd9f03e

1 file changed

Lines changed: 38 additions & 57 deletions

File tree

crates/ark/src/modules/positron/packages_pane.R

Lines changed: 38 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -8,73 +8,54 @@
88
# This file contains RPC functions for the packages pane.
99
# These functions are called via callMethod from the Positron R extension.
1010

11-
# Normalize a DESCRIPTION field value for display: collapse whitespace/newlines
12-
# into single spaces so a multi-line Description fits on one line in the UI.
13-
.ps.pkg_description_text <- function(value) {
14-
if (is.null(value) || is.na(value)) {
15-
return("")
16-
}
17-
value <- as.character(value)
18-
value <- gsub("\\s+", " ", value, perl = TRUE)
19-
trimws(value)
20-
}
21-
22-
# Normalize a Maintainer/Author value for display: collapse whitespace and strip
23-
# trailing email addresses in angle brackets (e.g., "Hadley Wickham <h@posit.co>"
24-
# becomes "Hadley Wickham").
25-
.ps.pkg_author_text <- function(value) {
26-
if (is.null(value) || is.na(value)) {
27-
return("")
28-
}
29-
value <- as.character(value)
30-
value <- gsub("\\s+", " ", value, perl = TRUE)
31-
value <- gsub("\\s*<[^>]+>", "", value, perl = TRUE)
32-
trimws(value)
33-
}
34-
35-
# Build the package list via utils::installed.packages(), optionally scoped to a
36-
# specific library path (used by the renv method).
3711
.ps.pkg_list_installed <- function(lib.loc = NULL) {
3812
ip <- utils::installed.packages(
3913
lib.loc = lib.loc,
4014
fields = c("Description", "Maintainer")
4115
)
42-
lapply(seq_len(nrow(ip)), function(i) {
43-
list(
44-
id = paste0(ip[i, "Package"], "-", ip[i, "Version"]),
45-
name = ip[i, "Package"],
46-
displayName = ip[i, "Package"],
47-
version = ip[i, "Version"],
48-
description = .ps.pkg_description_text(ip[i, "Description"]),
49-
author = .ps.pkg_author_text(ip[i, "Maintainer"])
50-
)
51-
})
16+
17+
name <- ip[, "Package"]
18+
version <- ip[, "Version"]
19+
id <- paste0(name, "-", version)
20+
# Collapse whitespace so a multi-line Description fits on one line in the UI.
21+
description <- trimws(gsub(
22+
"\\s+",
23+
" ",
24+
ifelse(is.na(ip[, "Description"]), "", ip[, "Description"]),
25+
perl = TRUE
26+
))
27+
# Strip "<email>" markers so "Hadley Wickham <h@posit.co>" becomes "Hadley Wickham".
28+
author <- trimws(gsub(
29+
"\\s*<[^>]+>",
30+
"",
31+
gsub(
32+
"\\s+",
33+
" ",
34+
ifelse(is.na(ip[, "Maintainer"]), "", ip[, "Maintainer"]),
35+
perl = TRUE
36+
),
37+
perl = TRUE
38+
))
39+
40+
unname(Map(
41+
list,
42+
id = id,
43+
name = name,
44+
displayName = name,
45+
version = version,
46+
description = description,
47+
author = author
48+
))
5249
}
5350

54-
# Return a list of installed packages
51+
# Return a list of installed packages. The pak/base/renv methods exist for
52+
# parity with install/update operations; for listing we always use
53+
# utils::installed.packages(), scoped to the renv library when requested.
5554
#' @export
5655
.ps.rpc.pkg_list <- function(method = c("pak", "base", "renv")) {
5756
method <- match.arg(method)
58-
switch(
59-
method,
60-
pak = {
61-
old_opt <- options(pak.no_extra_messages = TRUE)
62-
on.exit(options(old_opt), add = TRUE)
63-
pkgs <- pak::lib_status()
64-
lapply(seq_len(nrow(pkgs)), function(i) {
65-
list(
66-
id = paste0(pkgs$package[[i]], "-", pkgs$version[[i]]),
67-
name = pkgs$package[[i]],
68-
displayName = pkgs$package[[i]],
69-
version = as.character(pkgs$version[[i]]),
70-
description = .ps.pkg_description_text(pkgs$description[[i]]),
71-
author = .ps.pkg_author_text(pkgs$maintainer[[i]])
72-
)
73-
})
74-
},
75-
base = .ps.pkg_list_installed(),
76-
renv = .ps.pkg_list_installed(lib.loc = renv::paths$library())
77-
)
57+
lib.loc <- if (method == "renv") renv::paths$library() else NULL
58+
.ps.pkg_list_installed(lib.loc = lib.loc)
7859
}
7960

8061

0 commit comments

Comments
 (0)