11#   File src/library/utils/R/packages.R
22#   Part of the R package, https://www.R-project.org
33# 
4- #   Copyright (C) 1995-2024  The R Core Team
4+ #   Copyright (C) 1995-2025  The R Core Team
55# 
66#   This program is free software; you can redistribute it and/or modify
77#   it under the terms of the GNU General Public License as published by
@@ -44,6 +44,29 @@ function(contriburl = contrib.url(repos, type), method,
4444    res  <-  matrix (NA_character_ , 0L , length(fields ) +  1L ,
4545		  dimnames  =  list (NULL , c(fields , " Repository" 
4646
47+     url_to_cache_name  <-  function (url )
48+     {
49+           #  from rfc 3986
50+           re  <-  " ^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\\ ?([^#]*))?(#(.*))?" 
51+           p  <-  unlist(regmatches(url , regexec(re , url )))[c(2 ,4 ,6 ,7 ,9 )]
52+           names(p ) <-  c(" scheme" " authority" " path" " query" " fragment" 
53+ 
54+           if  (grepl(" @" p [" authority" fixed = TRUE )) {
55+               rea  <-  " //([^@]*)@(.*)" 
56+               pa  <-  unlist(regmatches(p [" authority" 
57+                                       regexec(rea , p [" authority" 2 ,3 )]
58+               names(pa ) <-  c(" userinfo" " hostport" 
59+               if  (nzchar(pa [" userinfo" 
60+                   #  replace user info by a hash
61+                   sha  <-  tools :: sha256sum(bytes = charToRaw(pa [" userinfo" 
62+                   url  <-  paste0(p [" scheme" " //" 
63+                                 substr(sha , 49 , 64 ), " @" pa [" hostport" 
64+                                 p [" path" p [" query" p [" fragment" 
65+               }
66+           }
67+           URLencode(url , TRUE )
68+     }
69+ 
4770    for (repos  in  unique(contriburl )) {
4871        localcran  <-  startsWith(repos , " file:" 
4972        if (localcran ) {
@@ -70,7 +93,8 @@ function(contriburl = contrib.url(repos, type), method,
7093            } else  {
7194                dest  <-  file.path(if (cache_user_dir ) tools :: R_user_dir(" base" " cache" 
7295                                  else  tempdir(),
73-                                   paste0(" repos_" repos , TRUE ), " .rds" 
96+                                   paste0(" repos_" repos ),
97+                                          " .rds" 
7498                if (file.exists(dest )) {
7599                    age  <-  difftime(timestamp , file.mtime(dest ), units  =  " secs" 
76100                    if (isTRUE(age  <  max_repo_cache_age )) {
0 commit comments