renovate 44.210.2 → 44.212.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (319) hide show
  1. package/dist/config/options/index.js +1 -1
  2. package/dist/config/options/index.js.map +1 -1
  3. package/dist/config/utils.js +2 -1
  4. package/dist/config/utils.js.map +1 -1
  5. package/dist/config/validation-helpers/regex-glob-matchers.js.map +1 -1
  6. package/dist/config/validation-helpers/utils.js +5 -1
  7. package/dist/config/validation-helpers/utils.js.map +1 -1
  8. package/dist/config/validation.js +8 -2
  9. package/dist/config/validation.js.map +1 -1
  10. package/dist/config-validator.js +1 -1
  11. package/dist/config-validator.js.map +1 -1
  12. package/dist/data/monorepo.js +8 -0
  13. package/dist/global-config-option-defaults.generated.js +1 -1
  14. package/dist/global-config-option-defaults.generated.js.map +1 -1
  15. package/dist/instrumentation/index.js +3 -2
  16. package/dist/instrumentation/index.js.map +1 -1
  17. package/dist/logger/bunyan.js +3 -2
  18. package/dist/logger/bunyan.js.map +1 -1
  19. package/dist/logger/pretty-stdout.js +2 -1
  20. package/dist/logger/pretty-stdout.js.map +1 -1
  21. package/dist/modules/datasource/apk/index.js +2 -2
  22. package/dist/modules/datasource/apk/index.js.map +1 -1
  23. package/dist/modules/datasource/artifactory/index.js +2 -3
  24. package/dist/modules/datasource/artifactory/index.js.map +1 -1
  25. package/dist/modules/datasource/bazel/index.js +2 -1
  26. package/dist/modules/datasource/bazel/index.js.map +1 -1
  27. package/dist/modules/datasource/cdnjs/index.js +2 -1
  28. package/dist/modules/datasource/cdnjs/index.js.map +1 -1
  29. package/dist/modules/datasource/common.d.ts +9 -0
  30. package/dist/modules/datasource/common.js +20 -2
  31. package/dist/modules/datasource/common.js.map +1 -1
  32. package/dist/modules/datasource/conda/index.js +2 -1
  33. package/dist/modules/datasource/conda/index.js.map +1 -1
  34. package/dist/modules/datasource/crate/index.js +2 -1
  35. package/dist/modules/datasource/crate/index.js.map +1 -1
  36. package/dist/modules/datasource/dart-version/index.js +2 -1
  37. package/dist/modules/datasource/dart-version/index.js.map +1 -1
  38. package/dist/modules/datasource/datasource.js +2 -2
  39. package/dist/modules/datasource/datasource.js.map +1 -1
  40. package/dist/modules/datasource/deb/url.js +3 -1
  41. package/dist/modules/datasource/deb/url.js.map +1 -1
  42. package/dist/modules/datasource/devbox/index.js +2 -1
  43. package/dist/modules/datasource/devbox/index.js.map +1 -1
  44. package/dist/modules/datasource/docker/common.js +10 -8
  45. package/dist/modules/datasource/docker/common.js.map +1 -1
  46. package/dist/modules/datasource/docker/ecr.js +2 -1
  47. package/dist/modules/datasource/docker/ecr.js.map +1 -1
  48. package/dist/modules/datasource/docker/index.js +20 -17
  49. package/dist/modules/datasource/docker/index.js.map +1 -1
  50. package/dist/modules/datasource/gitea-tags/base.js +2 -3
  51. package/dist/modules/datasource/gitea-tags/base.js.map +1 -1
  52. package/dist/modules/datasource/github-tags/index.js +2 -1
  53. package/dist/modules/datasource/github-tags/index.js.map +1 -1
  54. package/dist/modules/datasource/gitlab-tags/index.js +2 -3
  55. package/dist/modules/datasource/gitlab-tags/index.js.map +1 -1
  56. package/dist/modules/datasource/go/base.js +1 -1
  57. package/dist/modules/datasource/go/base.js.map +1 -1
  58. package/dist/modules/datasource/go/common.js +8 -2
  59. package/dist/modules/datasource/go/common.js.map +1 -1
  60. package/dist/modules/datasource/go/env.js +2 -1
  61. package/dist/modules/datasource/go/env.js.map +1 -1
  62. package/dist/modules/datasource/go/releases-goproxy.js +7 -5
  63. package/dist/modules/datasource/go/releases-goproxy.js.map +1 -1
  64. package/dist/modules/datasource/helm/index.js +2 -1
  65. package/dist/modules/datasource/helm/index.js.map +1 -1
  66. package/dist/modules/datasource/hexpm-bob/index.js +2 -1
  67. package/dist/modules/datasource/hexpm-bob/index.js.map +1 -1
  68. package/dist/modules/datasource/index.js +4 -3
  69. package/dist/modules/datasource/index.js.map +1 -1
  70. package/dist/modules/datasource/java-version/adoptium.js +3 -2
  71. package/dist/modules/datasource/java-version/adoptium.js.map +1 -1
  72. package/dist/modules/datasource/java-version/graalvm.js +2 -1
  73. package/dist/modules/datasource/java-version/graalvm.js.map +1 -1
  74. package/dist/modules/datasource/maven/index.js.map +1 -1
  75. package/dist/modules/datasource/maven/util.js +7 -10
  76. package/dist/modules/datasource/maven/util.js.map +1 -1
  77. package/dist/modules/datasource/npm/npmrc.js +2 -2
  78. package/dist/modules/datasource/npm/npmrc.js.map +1 -1
  79. package/dist/modules/datasource/nuget/v3.js +3 -5
  80. package/dist/modules/datasource/nuget/v3.js.map +1 -1
  81. package/dist/modules/datasource/packagist/index.js +4 -5
  82. package/dist/modules/datasource/packagist/index.js.map +1 -1
  83. package/dist/modules/datasource/pod/index.js +4 -4
  84. package/dist/modules/datasource/pod/index.js.map +1 -1
  85. package/dist/modules/datasource/pypi/index.js +19 -11
  86. package/dist/modules/datasource/pypi/index.js.map +1 -1
  87. package/dist/modules/datasource/python-version/index.js +2 -3
  88. package/dist/modules/datasource/python-version/index.js.map +1 -1
  89. package/dist/modules/datasource/repology/index.js +4 -3
  90. package/dist/modules/datasource/repology/index.js.map +1 -1
  91. package/dist/modules/datasource/rpm/providers/common.js +3 -1
  92. package/dist/modules/datasource/rpm/providers/common.js.map +1 -1
  93. package/dist/modules/datasource/rubygems/index.js +2 -5
  94. package/dist/modules/datasource/rubygems/index.js.map +1 -1
  95. package/dist/modules/datasource/rubygems/versions-endpoint-cache.js +13 -18
  96. package/dist/modules/datasource/rubygems/versions-endpoint-cache.js.map +1 -1
  97. package/dist/modules/datasource/terraform-module/base.js +2 -1
  98. package/dist/modules/datasource/terraform-module/base.js.map +1 -1
  99. package/dist/modules/datasource/terraform-provider/index.js +2 -3
  100. package/dist/modules/datasource/terraform-provider/index.js.map +1 -1
  101. package/dist/modules/manager/apm/extract.js +44 -17
  102. package/dist/modules/manager/apm/extract.js.map +1 -1
  103. package/dist/modules/manager/apm/index.js +5 -1
  104. package/dist/modules/manager/apm/index.js.map +1 -1
  105. package/dist/modules/manager/bazel-module/parser/context.js +0 -1
  106. package/dist/modules/manager/bazel-module/parser/context.js.map +1 -1
  107. package/dist/modules/manager/bundler/host-rules.js +4 -1
  108. package/dist/modules/manager/bundler/host-rules.js.map +1 -1
  109. package/dist/modules/manager/composer/range.js +1 -1
  110. package/dist/modules/manager/composer/range.js.map +1 -1
  111. package/dist/modules/manager/custom/utils.js +3 -1
  112. package/dist/modules/manager/custom/utils.js.map +1 -1
  113. package/dist/modules/manager/devbox/schema.js +2 -1
  114. package/dist/modules/manager/devbox/schema.js.map +1 -1
  115. package/dist/modules/manager/dockerfile/extract.js +10 -2
  116. package/dist/modules/manager/dockerfile/extract.js.map +1 -1
  117. package/dist/modules/manager/fingerprint.generated.js +3 -3
  118. package/dist/modules/manager/fingerprint.generated.js.map +1 -1
  119. package/dist/modules/manager/github-actions/parse.js +2 -1
  120. package/dist/modules/manager/github-actions/parse.js.map +1 -1
  121. package/dist/modules/manager/gomod/artifacts.js +5 -2
  122. package/dist/modules/manager/gomod/artifacts.js.map +1 -1
  123. package/dist/modules/manager/gradle/artifacts.js +5 -2
  124. package/dist/modules/manager/gradle/artifacts.js.map +1 -1
  125. package/dist/modules/manager/gradle/utils.js +2 -1
  126. package/dist/modules/manager/gradle/utils.js.map +1 -1
  127. package/dist/modules/manager/gradle-wrapper/utils.js +9 -5
  128. package/dist/modules/manager/gradle-wrapper/utils.js.map +1 -1
  129. package/dist/modules/manager/helm-values/util.js +1 -1
  130. package/dist/modules/manager/helm-values/util.js.map +1 -1
  131. package/dist/modules/manager/helmfile/artifacts.js +1 -1
  132. package/dist/modules/manager/helmfile/artifacts.js.map +1 -1
  133. package/dist/modules/manager/helmv3/artifacts.js +1 -1
  134. package/dist/modules/manager/helmv3/artifacts.js.map +1 -1
  135. package/dist/modules/manager/maven/extract.js +5 -2
  136. package/dist/modules/manager/maven/extract.js.map +1 -1
  137. package/dist/modules/manager/maven-wrapper/artifacts.js +3 -2
  138. package/dist/modules/manager/maven-wrapper/artifacts.js.map +1 -1
  139. package/dist/modules/manager/mise/artifacts.js +2 -1
  140. package/dist/modules/manager/mise/artifacts.js.map +1 -1
  141. package/dist/modules/manager/mise/extract.js.map +1 -1
  142. package/dist/modules/manager/nix/extract.js +1 -2
  143. package/dist/modules/manager/nix/extract.js.map +1 -1
  144. package/dist/modules/manager/npm/artifacts.js +3 -1
  145. package/dist/modules/manager/npm/artifacts.js.map +1 -1
  146. package/dist/modules/manager/npm/extract/common/dependency.js +4 -1
  147. package/dist/modules/manager/npm/extract/common/dependency.js.map +1 -1
  148. package/dist/modules/manager/npm/extract/common/package-file.js +2 -1
  149. package/dist/modules/manager/npm/extract/common/package-file.js.map +1 -1
  150. package/dist/modules/manager/npm/extract/index.js.map +1 -1
  151. package/dist/modules/manager/npm/extract/post/locked-versions.js.map +1 -1
  152. package/dist/modules/manager/npm/npmrc.js +2 -1
  153. package/dist/modules/manager/npm/npmrc.js.map +1 -1
  154. package/dist/modules/manager/npm/post-update/index.js +2 -1
  155. package/dist/modules/manager/npm/post-update/index.js.map +1 -1
  156. package/dist/modules/manager/npm/post-update/npm.js +2 -3
  157. package/dist/modules/manager/npm/post-update/npm.js.map +1 -1
  158. package/dist/modules/manager/npm/post-update/yarn.js.map +1 -1
  159. package/dist/modules/manager/npm/schema.js +6 -2
  160. package/dist/modules/manager/npm/schema.js.map +1 -1
  161. package/dist/modules/manager/npm/update/dependency/index.js +3 -2
  162. package/dist/modules/manager/npm/update/dependency/index.js.map +1 -1
  163. package/dist/modules/manager/npm/update/locked-dependency/common/parent-version.js +6 -2
  164. package/dist/modules/manager/npm/update/locked-dependency/common/parent-version.js.map +1 -1
  165. package/dist/modules/manager/npm/update/locked-dependency/package-lock/get-locked.js +2 -1
  166. package/dist/modules/manager/npm/update/locked-dependency/package-lock/get-locked.js.map +1 -1
  167. package/dist/modules/manager/nuget/package-tree.js +2 -1
  168. package/dist/modules/manager/nuget/package-tree.js.map +1 -1
  169. package/dist/modules/manager/paket/update-locked.js +4 -1
  170. package/dist/modules/manager/paket/update-locked.js.map +1 -1
  171. package/dist/modules/manager/pipenv/extract.js +4 -1
  172. package/dist/modules/manager/pipenv/extract.js.map +1 -1
  173. package/dist/modules/platform/azure/azure-helper.js +2 -1
  174. package/dist/modules/platform/azure/azure-helper.js.map +1 -1
  175. package/dist/modules/platform/azure/index.js +10 -6
  176. package/dist/modules/platform/azure/index.js.map +1 -1
  177. package/dist/modules/platform/bitbucket/index.js +13 -6
  178. package/dist/modules/platform/bitbucket/index.js.map +1 -1
  179. package/dist/modules/platform/bitbucket-server/index.js +13 -9
  180. package/dist/modules/platform/bitbucket-server/index.js.map +1 -1
  181. package/dist/modules/platform/codecommit/index.js +2 -2
  182. package/dist/modules/platform/codecommit/index.js.map +1 -1
  183. package/dist/modules/platform/gerrit/client.js +4 -1
  184. package/dist/modules/platform/gerrit/client.js.map +1 -1
  185. package/dist/modules/platform/gerrit/index.js +3 -2
  186. package/dist/modules/platform/gerrit/index.js.map +1 -1
  187. package/dist/modules/platform/gitea/gitea-helper.js +5 -4
  188. package/dist/modules/platform/gitea/gitea-helper.js.map +1 -1
  189. package/dist/modules/platform/gitea/index.js +11 -4
  190. package/dist/modules/platform/gitea/index.js.map +1 -1
  191. package/dist/modules/platform/github/index.js +37 -24
  192. package/dist/modules/platform/github/index.js.map +1 -1
  193. package/dist/modules/platform/gitlab/index.js +16 -9
  194. package/dist/modules/platform/gitlab/index.js.map +1 -1
  195. package/dist/modules/platform/scm-manager/index.js +4 -1
  196. package/dist/modules/platform/scm-manager/index.js.map +1 -1
  197. package/dist/modules/platform/scm-manager/utils.js +2 -1
  198. package/dist/modules/platform/scm-manager/utils.js.map +1 -1
  199. package/dist/modules/versioning/cargo/index.js.map +1 -1
  200. package/dist/modules/versioning/composer/index.js +2 -1
  201. package/dist/modules/versioning/composer/index.js.map +1 -1
  202. package/dist/modules/versioning/conan/common.js +4 -1
  203. package/dist/modules/versioning/conan/common.js.map +1 -1
  204. package/dist/modules/versioning/debian/index.js +2 -1
  205. package/dist/modules/versioning/debian/index.js.map +1 -1
  206. package/dist/modules/versioning/gradle/compare.js +2 -1
  207. package/dist/modules/versioning/gradle/compare.js.map +1 -1
  208. package/dist/modules/versioning/hex/index.js +2 -1
  209. package/dist/modules/versioning/hex/index.js.map +1 -1
  210. package/dist/modules/versioning/julia/index.js.map +1 -1
  211. package/dist/modules/versioning/maven/compare.js +17 -7
  212. package/dist/modules/versioning/maven/compare.js.map +1 -1
  213. package/dist/modules/versioning/npm/index.js +2 -1
  214. package/dist/modules/versioning/npm/index.js.map +1 -1
  215. package/dist/modules/versioning/npm/range.js.map +1 -1
  216. package/dist/modules/versioning/paket/index.js +2 -1
  217. package/dist/modules/versioning/paket/index.js.map +1 -1
  218. package/dist/modules/versioning/paket/range.js +7 -3
  219. package/dist/modules/versioning/paket/range.js.map +1 -1
  220. package/dist/modules/versioning/pep440/index.js +2 -1
  221. package/dist/modules/versioning/pep440/index.js.map +1 -1
  222. package/dist/modules/versioning/poetry/index.js +2 -1
  223. package/dist/modules/versioning/poetry/index.js.map +1 -1
  224. package/dist/modules/versioning/regex/index.js +1 -1
  225. package/dist/modules/versioning/regex/index.js.map +1 -1
  226. package/dist/modules/versioning/rez/index.js +2 -1
  227. package/dist/modules/versioning/rez/index.js.map +1 -1
  228. package/dist/modules/versioning/vcpkg/index.js +2 -1
  229. package/dist/modules/versioning/vcpkg/index.js.map +1 -1
  230. package/dist/util/cache/package/impl/base.js +2 -1
  231. package/dist/util/cache/package/impl/base.js.map +1 -1
  232. package/dist/util/cache/package/with-cache.js +2 -1
  233. package/dist/util/cache/package/with-cache.js.map +1 -1
  234. package/dist/util/check-token.js +7 -4
  235. package/dist/util/check-token.js.map +1 -1
  236. package/dist/util/exec/utils.js +4 -1
  237. package/dist/util/exec/utils.js.map +1 -1
  238. package/dist/util/git/auth.js +5 -1
  239. package/dist/util/git/auth.js.map +1 -1
  240. package/dist/util/git/error.js.map +1 -1
  241. package/dist/util/git/private-key.js +5 -0
  242. package/dist/util/git/private-key.js.map +1 -1
  243. package/dist/util/host-rules.js +5 -3
  244. package/dist/util/host-rules.js.map +1 -1
  245. package/dist/util/http/cache/abstract-http-cache-provider.js +3 -2
  246. package/dist/util/http/cache/abstract-http-cache-provider.js.map +1 -1
  247. package/dist/util/http/cache/package-http-cache-provider.js +2 -1
  248. package/dist/util/http/cache/package-http-cache-provider.js.map +1 -1
  249. package/dist/util/http/github.js +15 -11
  250. package/dist/util/http/github.js.map +1 -1
  251. package/dist/util/http/gitlab.js +5 -4
  252. package/dist/util/http/gitlab.js.map +1 -1
  253. package/dist/util/http/http.js +2 -1
  254. package/dist/util/http/http.js.map +1 -1
  255. package/dist/util/http/jwt.js +2 -1
  256. package/dist/util/http/jwt.js.map +1 -1
  257. package/dist/util/http/retry-after.js +2 -1
  258. package/dist/util/http/retry-after.js.map +1 -1
  259. package/dist/util/http/status.js +95 -0
  260. package/dist/util/http/status.js.map +1 -0
  261. package/dist/util/merge-confidence/index.js +3 -2
  262. package/dist/util/merge-confidence/index.js.map +1 -1
  263. package/dist/util/package-rules/current-version.js +4 -1
  264. package/dist/util/package-rules/current-version.js.map +1 -1
  265. package/dist/util/package-rules/index.js +7 -3
  266. package/dist/util/package-rules/index.js.map +1 -1
  267. package/dist/util/schema-utils/index.js +5 -0
  268. package/dist/util/schema-utils/index.js.map +1 -1
  269. package/dist/workers/global/config/parse/host-rules-from-env.js +2 -1
  270. package/dist/workers/global/config/parse/host-rules-from-env.js.map +1 -1
  271. package/dist/workers/repository/common.js +4 -1
  272. package/dist/workers/repository/common.js.map +1 -1
  273. package/dist/workers/repository/config-migration/branch/index.js +2 -1
  274. package/dist/workers/repository/config-migration/branch/index.js.map +1 -1
  275. package/dist/workers/repository/dependency-dashboard.js +6 -2
  276. package/dist/workers/repository/dependency-dashboard.js.map +1 -1
  277. package/dist/workers/repository/finalize/repository-statistics.js +4 -1
  278. package/dist/workers/repository/finalize/repository-statistics.js.map +1 -1
  279. package/dist/workers/repository/init/merge.js +13 -3
  280. package/dist/workers/repository/init/merge.js.map +1 -1
  281. package/dist/workers/repository/onboarding/branch/check.js +2 -1
  282. package/dist/workers/repository/onboarding/branch/check.js.map +1 -1
  283. package/dist/workers/repository/onboarding/pr/pr-list.js +4 -2
  284. package/dist/workers/repository/onboarding/pr/pr-list.js.map +1 -1
  285. package/dist/workers/repository/process/extract-update.js +4 -1
  286. package/dist/workers/repository/process/extract-update.js.map +1 -1
  287. package/dist/workers/repository/process/lookup/digest.js +2 -1
  288. package/dist/workers/repository/process/lookup/digest.js.map +1 -1
  289. package/dist/workers/repository/process/lookup/generate.js +1 -1
  290. package/dist/workers/repository/process/lookup/generate.js.map +1 -1
  291. package/dist/workers/repository/process/lookup/index.js +4 -1
  292. package/dist/workers/repository/process/lookup/index.js.map +1 -1
  293. package/dist/workers/repository/process/lookup/utils.js +7 -1
  294. package/dist/workers/repository/process/lookup/utils.js.map +1 -1
  295. package/dist/workers/repository/process/vulnerabilities.js +10 -3
  296. package/dist/workers/repository/process/vulnerabilities.js.map +1 -1
  297. package/dist/workers/repository/reconfigure/index.js +2 -1
  298. package/dist/workers/repository/reconfigure/index.js.map +1 -1
  299. package/dist/workers/repository/update/branch/auto-replace.js +6 -2
  300. package/dist/workers/repository/update/branch/auto-replace.js.map +1 -1
  301. package/dist/workers/repository/update/branch/errors.js +2 -1
  302. package/dist/workers/repository/update/branch/errors.js.map +1 -1
  303. package/dist/workers/repository/update/branch/execute-post-upgrade-commands.js +2 -2
  304. package/dist/workers/repository/update/branch/execute-post-upgrade-commands.js.map +1 -1
  305. package/dist/workers/repository/update/branch/get-updated.js +1 -2
  306. package/dist/workers/repository/update/branch/get-updated.js.map +1 -1
  307. package/dist/workers/repository/update/branch/index.js +2 -1
  308. package/dist/workers/repository/update/branch/index.js.map +1 -1
  309. package/dist/workers/repository/update/branch/status-checks.js +2 -1
  310. package/dist/workers/repository/update/branch/status-checks.js.map +1 -1
  311. package/dist/workers/repository/update/pr/body/index.js.map +1 -1
  312. package/dist/workers/repository/update/pr/changelog/release-notes.js +6 -3
  313. package/dist/workers/repository/update/pr/changelog/release-notes.js.map +1 -1
  314. package/dist/workers/repository/update/pr/index.js +7 -3
  315. package/dist/workers/repository/update/pr/index.js.map +1 -1
  316. package/dist/workers/repository/updates/generate.js +6 -3
  317. package/dist/workers/repository/updates/generate.js.map +1 -1
  318. package/package.json +2 -2
  319. package/renovate-schema.json +2 -2
@@ -1 +1 @@
1
- {"version":3,"file":"config-validator.js","names":["getFileConfig"],"sources":["../lib/config-validator.ts"],"sourcesContent":["#!/usr/bin/env node\nimport 'source-map-support/register.js';\nimport './punycode.cjs';\n\nimport { styleText } from 'node:util';\nimport { isNonEmptyStringAndNotWhitespace } from '@sindresorhus/is';\nimport { Command, CommanderError } from 'commander';\nimport { dequal } from 'dequal';\nimport { diffLines } from 'diff';\nimport fs from 'fs-extra';\nimport { getConfigFileNames } from './config/app-strings.ts';\nimport { GlobalConfig } from './config/global.ts';\nimport { massageConfig } from './config/massage.ts';\nimport { migrateConfig } from './config/migration.ts';\nimport type { RenovateConfig } from './config/types.ts';\nimport { validateConfig } from './config/validation.ts';\nimport { pkg } from './expose.ts';\nimport { init, logger } from './logger/index.ts';\nimport { getEnv } from './util/env.ts';\nimport { add as addHostRule } from './util/host-rules.ts';\nimport { regEx, regexEngineStatus } from './util/regex.ts';\nimport { getConfig as getFileConfig } from './workers/global/config/parse/file.ts';\nimport { parseConfigs } from './workers/global/config/parse/index.ts';\nimport { getParsedContent } from './workers/global/config/parse/util.ts';\n\nawait init();\n\nconst { pathExists, readFile } = fs;\n\nlet returnVal = 0;\n\n/**\n * Make sure that we've resolved configuration from the different places that Renovate users would expect them to be specified\n *\n * This then allows a `configType=repo` config to i.e. be validated alongside a `config.js` or `env RENOVATE_ALLOWED_COMMANDS=...`\n *\n * Note that we intentionally don't fully initialize Renovate and its modules, as we're not fully running, and it would require a Platform to be configured\n * */\nasync function partiallyGlobalInitialize(): Promise<void> {\n // NOTE that this doesn't allow command-line arguments\n const globalConfig = await parseConfigs(getEnv(), []);\n GlobalConfig.set(globalConfig);\n\n if (globalConfig.hostRules) {\n // this is the self-hosted admin's own config, so its `headers` are exempt from `allowedHeaders` altogether - see `hostRules.add()`\n for (const hostRule of globalConfig.hostRules) {\n addHostRule(hostRule, { trusted: true });\n }\n }\n}\n\nasync function validate(\n configType: 'global' | 'repo',\n desc: string,\n config: RenovateConfig,\n strict: boolean,\n isPreset = false,\n): Promise<void> {\n if (config.hostRules) {\n // a `global` config is the self-hosted administrator's own, so its `headers` are exempt from `allowedHeaders` altogether - see `hostRules.add()`; a `repo` config's `hostRules` are still constrained by this instance's `allowedHeaders`\n for (const hostRule of config.hostRules) {\n addHostRule(hostRule, { trusted: configType === 'global' });\n }\n }\n const { isMigrated, migratedConfig } = migrateConfig(config);\n if (isMigrated) {\n logger.warn(\n {\n oldConfig: config,\n newConfig: migratedConfig,\n },\n 'Config migration necessary',\n );\n const changedObjects = diffLines(\n JSON.stringify(config, null, 2),\n JSON.stringify(migratedConfig, null, 2),\n { ignoreWhitespace: false, newlineIsToken: false },\n );\n const added = styleText('green', '+ ');\n const removed = styleText('red', '- ');\n const msg = changedObjects\n .flatMap((part) => {\n let linePrefix: string;\n if (part.added) {\n linePrefix = added;\n } else if (part.removed) {\n linePrefix = removed;\n } else {\n linePrefix = ' ';\n }\n return part.value\n .split('\\n')\n .filter(isNonEmptyStringAndNotWhitespace)\n .map((line) =>\n line.replace(regEx(/^(?<ws> *)/), `${linePrefix}$<ws>`),\n );\n })\n .join('\\n');\n // oxlint-disable-next-line renovate/logger-static-message -- the multi-line, colorized diff must be interpolated to stay readable; as a metadata field it is JSON-escaped onto one line\n logger.warn(`Config migration diff:\\n${msg}`);\n if (strict) {\n returnVal = 1;\n }\n }\n const massagedConfig = massageConfig(migratedConfig);\n const res = await validateConfig(configType, massagedConfig, isPreset);\n if (res.errors.length) {\n logger.error(\n { file: desc, errors: res.errors },\n 'Found errors in configuration',\n );\n returnVal = 1;\n }\n if (res.warnings.length) {\n logger.warn(\n { file: desc, warnings: res.warnings },\n 'Found errors in configuration',\n );\n returnVal = 1;\n }\n}\n\ninterface PackageJson {\n renovate?: RenovateConfig;\n 'renovate-config'?: Record<string, RenovateConfig>;\n}\n\n(async () => {\n await partiallyGlobalInitialize();\n\n const program = new Command('renovate-config-validator')\n .summary('Validate Renovate configuration files')\n .description(\n `Validate your Renovate configuration (repo config, shared presets or global configuration) files\\n` +\n // oxlint-disable-next-line renovate/no-hardcoded-docs-url -- CLI help text, no config available\n 'If no [config-files...] are given, renovate-config-validator will look at the default config file locations (https://docs.renovatebot.com/configuration-options/)',\n )\n .addHelpText(\n 'after',\n // oxlint-disable-next-line renovate/no-hardcoded-docs-url -- CLI help text, no config available\n `\nWhen specifying [config-files...], Renovate will treat them as global self-hosted configuration files. You can disable this behaviour with --no-global\n\nExamples:\n\n $ renovate-config-validator\n $ renovate-config-validator --strict\n $ renovate-config-validator first_config.json\n $ renovate-config-validator --strict config.js\n $ renovate-config-validator --no-global renovate.json5\n $ env RENOVATE_CONFIG_FILE=obscure-name.json renovate-config-validator\n\nGlobal configuration:\n\nIf you have specified global self-hosted configuration (https://docs.renovatebot.com/self-hosted-configuration/) in environment variables or in a \\`config.js\\`, this will be detected:\n\n $ env RENOVATE_ALLOWED_ENV='[\"GO*\"]' renovate-config-validator\n # if passing the filename, make sure it's not validating as a global config\n $ env RENOVATE_ALLOWED_ENV='[\"GO*\"]' renovate-config-validator --no-global renovate.json`,\n )\n .argument('[config-files...]')\n .version(pkg.version, '-v, --version')\n .option(\n '--strict',\n 'Fail command if any configuration warnings, errors, or a migration is needed',\n )\n .option(\n '--no-global',\n 'When specifying [config-files], do not treat them as global self-hosted configuration file(s)',\n true,\n )\n // allow us to manage the exit code\n .exitOverride();\n\n program.action(async (files, opts) => {\n const strict = opts.strict ?? false;\n let filesValidated = 0;\n\n // without RE2, patterns are checked by RegExp, which accepts syntax RE2 rejects (e.g. lookahead)\n if (regexEngineStatus.type === 'unavailable') {\n logger.warn(\n { err: regexEngineStatus.err },\n 'RE2 not usable, falling back to RegExp: regex validation may be inaccurate',\n );\n } else if (regexEngineStatus.type === 'ignored') {\n logger.debug(\n 'RE2 ignored via RENOVATE_X_IGNORE_RE2: regex validation may be inaccurate',\n );\n }\n\n if (files.length) {\n let isGlobalConfig = true;\n if (opts.global === false) {\n isGlobalConfig = false;\n }\n const configType = isGlobalConfig ? 'global' : 'repo';\n for (const file of files) {\n try {\n if (!(await pathExists(file))) {\n returnVal = 1;\n logger.error({ file }, 'File does not exist');\n break;\n }\n const parsedContent = await getParsedContent(file);\n try {\n logger.info(`Validating ${file} as ${configType} config`);\n await validate(configType, file, parsedContent, strict);\n } catch (err) {\n logger.warn({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n } catch (err) {\n logger.warn({ file, err }, 'File could not be parsed');\n returnVal = 1;\n }\n\n filesValidated++;\n }\n } else {\n for (const file of getConfigFileNames().filter(\n (name) => name !== 'package.json',\n )) {\n try {\n if (!(await pathExists(file))) {\n continue;\n }\n const parsedContent = await getParsedContent(file);\n try {\n logger.info(`Validating ${file}`);\n await validate('repo', file, parsedContent, strict);\n } catch (err) {\n logger.warn({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n } catch (err) {\n logger.warn({ file, err }, 'File could not be parsed');\n returnVal = 1;\n }\n\n filesValidated++;\n }\n try {\n const pkgJson = JSON.parse(\n await readFile('package.json', 'utf8'),\n ) as PackageJson;\n if (pkgJson.renovate) {\n logger.info(`Validating package.json > renovate`);\n await validate(\n 'repo',\n 'package.json > renovate',\n pkgJson.renovate,\n strict,\n );\n\n filesValidated++;\n }\n if (pkgJson['renovate-config']) {\n logger.info(`Validating package.json > renovate-config`);\n for (const presetConfig of Object.values(\n pkgJson['renovate-config'],\n )) {\n await validate(\n 'repo',\n 'package.json > renovate-config',\n presetConfig,\n strict,\n true,\n );\n\n filesValidated++;\n }\n }\n } catch {\n // ignore\n }\n try {\n const env = getEnv();\n const fileConfig = await getFileConfig(env);\n if (!dequal(fileConfig, {})) {\n const file = env.RENOVATE_CONFIG_FILE ?? 'config.js';\n logger.info(`Validating ${file}`);\n try {\n await validate('global', file, fileConfig, strict);\n } catch (err) {\n logger.error({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n filesValidated++;\n }\n } catch {\n // ignore\n }\n }\n if (returnVal === 0 && filesValidated) {\n logger.info(\n `Config validated successfully against ${filesValidated} file(s)`,\n );\n } else if (!filesValidated) {\n logger.warn(`No files to perform configuration validation against`);\n }\n // Use exitCode (not process.exit) so async log streams can flush\n process.exitCode = returnVal;\n });\n\n await program.parseAsync();\n})().catch((e) => {\n // Commander throws an error at the end of Action execution i.e. as part of the `help` and `version` commands, and so we don't want to return an error code in this case\n if (\n e instanceof CommanderError &&\n (e.code === 'commander.helpDisplayed' || e.code === 'commander.version')\n ) {\n return;\n }\n\n // oxlint-disable-next-line no-console -- intentional: display critical error on CLI\n console.error(e);\n process.exit(99);\n});\n"],"mappings":"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"}
1
+ {"version":3,"file":"config-validator.js","names":["getFileConfig"],"sources":["../lib/config-validator.ts"],"sourcesContent":["#!/usr/bin/env node\nimport 'source-map-support/register.js';\nimport './punycode.cjs';\n\nimport { styleText } from 'node:util';\nimport { isNonEmptyStringAndNotWhitespace } from '@sindresorhus/is';\nimport { Command, CommanderError } from 'commander';\nimport { dequal } from 'dequal';\nimport { diffLines } from 'diff';\nimport fs from 'fs-extra';\nimport { getConfigFileNames } from './config/app-strings.ts';\nimport { GlobalConfig } from './config/global.ts';\nimport { massageConfig } from './config/massage.ts';\nimport { migrateConfig } from './config/migration.ts';\nimport type { RenovateConfig } from './config/types.ts';\nimport { validateConfig } from './config/validation.ts';\nimport { pkg } from './expose.ts';\nimport { init, logger } from './logger/index.ts';\nimport { getEnv } from './util/env.ts';\nimport { add as addHostRule } from './util/host-rules.ts';\nimport { regEx, regexEngineStatus } from './util/regex.ts';\nimport { getConfig as getFileConfig } from './workers/global/config/parse/file.ts';\nimport { parseConfigs } from './workers/global/config/parse/index.ts';\nimport { getParsedContent } from './workers/global/config/parse/util.ts';\n\nawait init();\n\nconst { pathExists, readFile } = fs;\n\nlet returnVal = 0;\n\n/**\n * Make sure that we've resolved configuration from the different places that Renovate users would expect them to be specified\n *\n * This then allows a `configType=repo` config to i.e. be validated alongside a `config.js` or `env RENOVATE_ALLOWED_COMMANDS=...`\n *\n * Note that we intentionally don't fully initialize Renovate and its modules, as we're not fully running, and it would require a Platform to be configured\n * */\nasync function partiallyGlobalInitialize(): Promise<void> {\n // NOTE that this doesn't allow command-line arguments\n const globalConfig = await parseConfigs(getEnv(), []);\n GlobalConfig.set(globalConfig);\n\n if (globalConfig.hostRules) {\n // this is the self-hosted admin's own config, so its `headers` are exempt from `allowedHeaders` altogether - see `hostRules.add()`\n for (const hostRule of globalConfig.hostRules) {\n addHostRule(hostRule, { trusted: true });\n }\n }\n}\n\nasync function validate(\n configType: 'global' | 'repo',\n desc: string,\n config: RenovateConfig,\n strict: boolean,\n isPreset = false,\n): Promise<void> {\n if (config.hostRules) {\n // a `global` config is the self-hosted administrator's own, so its `headers` are exempt from `allowedHeaders` altogether - see `hostRules.add()`; a `repo` config's `hostRules` are still constrained by this instance's `allowedHeaders`\n for (const hostRule of config.hostRules) {\n addHostRule(hostRule, { trusted: configType === 'global' });\n }\n }\n const { isMigrated, migratedConfig } = migrateConfig(config);\n if (isMigrated) {\n logger.warn(\n {\n oldConfig: config,\n newConfig: migratedConfig,\n },\n 'Config migration necessary',\n );\n const changedObjects = diffLines(\n JSON.stringify(config, null, 2),\n JSON.stringify(migratedConfig, null, 2),\n { ignoreWhitespace: false, newlineIsToken: false },\n );\n const added = styleText('green', '+ ');\n const removed = styleText('red', '- ');\n const msg = changedObjects\n .flatMap((part) => {\n let linePrefix: string;\n if (part.added) {\n linePrefix = added;\n } else if (part.removed) {\n linePrefix = removed;\n } else {\n linePrefix = ' ';\n }\n return part.value\n .split('\\n')\n .filter(isNonEmptyStringAndNotWhitespace)\n .map((line) =>\n line.replace(regEx(/^(?<ws> *)/), `${linePrefix}$<ws>`),\n );\n })\n .join('\\n');\n // oxlint-disable-next-line renovate/logger-static-message -- the multi-line, colorized diff must be interpolated to stay readable; as a metadata field it is JSON-escaped onto one line\n logger.warn(`Config migration diff:\\n${msg}`);\n if (strict) {\n returnVal = 1;\n }\n }\n const massagedConfig = massageConfig(migratedConfig);\n const res = await validateConfig(configType, massagedConfig, isPreset);\n if (res.errors.length) {\n logger.error(\n { file: desc, errors: res.errors },\n 'Found errors in configuration',\n );\n returnVal = 1;\n }\n if (res.warnings.length) {\n logger.warn(\n { file: desc, warnings: res.warnings },\n 'Found errors in configuration',\n );\n returnVal = 1;\n }\n}\n\ninterface PackageJson {\n renovate?: RenovateConfig;\n 'renovate-config'?: Record<string, RenovateConfig>;\n}\n\n(async () => {\n await partiallyGlobalInitialize();\n\n const program = new Command('renovate-config-validator')\n .summary('Validate Renovate configuration files')\n .description(\n `Validate your Renovate configuration (repo config, shared presets or global configuration) files\\n` +\n // oxlint-disable-next-line renovate/no-hardcoded-docs-url -- CLI help text, no config available\n 'If no [config-files...] are given, renovate-config-validator will look at the default config file locations (https://docs.renovatebot.com/configuration-options/)',\n )\n .addHelpText(\n 'after',\n // oxlint-disable-next-line renovate/no-hardcoded-docs-url -- CLI help text, no config available\n `\nWhen specifying [config-files...], Renovate will treat them as global self-hosted configuration files. You can disable this behaviour with --no-global\n\nExamples:\n\n $ renovate-config-validator\n $ renovate-config-validator --strict\n $ renovate-config-validator first_config.json\n $ renovate-config-validator --strict config.js\n $ renovate-config-validator --no-global renovate.json5\n $ env RENOVATE_CONFIG_FILE=obscure-name.json renovate-config-validator\n\nGlobal configuration:\n\nIf you have specified global self-hosted configuration (https://docs.renovatebot.com/self-hosted-configuration/) in environment variables or in a \\`config.js\\`, this will be detected:\n\n $ env RENOVATE_ALLOWED_ENV='[\"GO*\"]' renovate-config-validator\n # if passing the filename, make sure it's not validating as a global config\n $ env RENOVATE_ALLOWED_ENV='[\"GO*\"]' renovate-config-validator --no-global renovate.json`,\n )\n .argument('[config-files...]')\n .version(pkg.version, '-v, --version')\n .option(\n '--strict',\n 'Fail command if any configuration warnings, errors, or a migration is needed',\n )\n .option(\n '--no-global',\n 'When specifying [config-files], do not treat them as global self-hosted configuration file(s)',\n true,\n )\n // allow us to manage the exit code\n .exitOverride();\n\n program.action(async (files, opts) => {\n const strict = opts.strict ?? false;\n let filesValidated = 0;\n\n // without RE2, patterns are checked by RegExp, which accepts syntax RE2 rejects (e.g. lookahead)\n if (regexEngineStatus.type === 'unavailable') {\n logger.warn(\n { err: regexEngineStatus.err },\n 'RE2 not usable, falling back to RegExp: regex validation may be inaccurate',\n );\n } else if (regexEngineStatus.type === 'ignored') {\n logger.debug(\n 'RE2 ignored via RENOVATE_X_IGNORE_RE2: regex validation may be inaccurate',\n );\n }\n\n if (files.length) {\n let isGlobalConfig = true;\n if (opts.global === false) {\n isGlobalConfig = false;\n }\n const configType = isGlobalConfig ? 'global' : 'repo';\n for (const file of files) {\n try {\n if (!(await pathExists(file))) {\n returnVal = 1;\n logger.error({ file }, 'File does not exist');\n break;\n }\n const parsedContent = await getParsedContent(file);\n try {\n logger.info(`Validating ${file} as ${configType} config`);\n await validate(configType, file, parsedContent, strict);\n } catch (err) {\n logger.warn({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n } catch (err) {\n logger.warn({ file, err }, 'File could not be parsed');\n returnVal = 1;\n }\n\n filesValidated++;\n }\n } else {\n for (const file of getConfigFileNames().filter(\n (name) => name !== 'package.json',\n )) {\n try {\n if (!(await pathExists(file))) {\n continue;\n }\n const parsedContent = await getParsedContent(file);\n try {\n logger.info(`Validating ${file}`);\n await validate('repo', file, parsedContent, strict);\n } catch (err) {\n logger.warn({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n } catch (err) {\n logger.warn({ file, err }, 'File could not be parsed');\n returnVal = 1;\n }\n\n filesValidated++;\n }\n try {\n const pkgJson = JSON.parse(\n await readFile('package.json', 'utf8'),\n ) as PackageJson;\n if (pkgJson.renovate) {\n logger.info(`Validating package.json > renovate`);\n await validate(\n 'repo',\n 'package.json > renovate',\n pkgJson.renovate,\n strict,\n );\n\n filesValidated++;\n }\n if (pkgJson['renovate-config']) {\n logger.info(`Validating package.json > renovate-config`);\n for (const presetConfig of Object.values(\n pkgJson['renovate-config'],\n )) {\n await validate(\n 'repo',\n 'package.json > renovate-config',\n presetConfig,\n strict,\n true,\n );\n\n filesValidated++;\n }\n }\n } catch {\n // ignore\n }\n try {\n const env = getEnv();\n const fileConfig = await getFileConfig(env);\n if (!dequal(fileConfig, {})) {\n const file = env.RENOVATE_CONFIG_FILE ?? 'config.js';\n logger.info(`Validating ${file}`);\n try {\n await validate('global', file, fileConfig, strict);\n } catch (err) {\n logger.error({ file, err }, 'File is not valid Renovate config');\n returnVal = 1;\n }\n filesValidated++;\n }\n } catch {\n // ignore\n }\n }\n if (returnVal === 0 && filesValidated) {\n logger.info(\n `Config validated successfully against ${filesValidated} file(s)`,\n );\n } else if (!filesValidated) {\n logger.warn(`No files to perform configuration validation against`);\n }\n // Use exitCode (not process.exit) so async log streams can flush\n process.exitCode = returnVal;\n });\n\n await program.parseAsync();\n})().catch((e) => {\n // Commander throws an error at the end of Action execution i.e. as part of the `help` and `version` commands, and so we don't want to return an error code in this case\n if (\n e instanceof CommanderError &&\n ['commander.helpDisplayed', 'commander.version'].includes(e.code)\n ) {\n return;\n }\n\n // oxlint-disable-next-line no-console -- intentional: display critical error on CLI\n console.error(e);\n process.exit(99);\n});\n"],"mappings":"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"}
@@ -126,11 +126,14 @@ var repoGroups = {
126
126
  "capacitor": "https://github.com/ionic-team/capacitor",
127
127
  "cedar": "https://github.com/cedarjs/cedar",
128
128
  "chakra-ui": "https://github.com/chakra-ui/chakra-ui",
129
+ "chat-sdk": "https://github.com/vercel/chat",
129
130
  "chromely": "https://github.com/chromelyapps/Chromely",
130
131
  "citation-js": "https://github.com/citation-js/citation-js",
131
132
  "ckeditor": ["https://github.com/ckeditor/ckeditor5", "https://github.com/ckeditor/ckeditor5-premium-features"],
132
133
  "clarity": "https://github.com/vmware/clarity",
133
134
  "clearscript": ["https://github.com/microsoft/ClearScript", "https://github.com/Microsoft/ClearScript"],
135
+ "cloudevents-sdk-csharp": "https://github.com/cloudevents/sdk-csharp",
136
+ "cloudevents-sdk-java": "https://github.com/cloudevents/sdk-java",
134
137
  "commitlint": "https://github.com/conventional-changelog/commitlint",
135
138
  "confect": "https://github.com/rjdellecese/confect",
136
139
  "conform": "https://github.com/edmundhung/conform",
@@ -366,6 +369,11 @@ var repoGroups = {
366
369
  "eslint": "https://github.com/eslint/eslint",
367
370
  "eslint-config-globex": "https://github.com/GlobexDesignsInc/eslint-config-globex",
368
371
  "eslint-stylistic": "https://github.com/eslint-stylistic/eslint-stylistic",
372
+ "excel-dna": [
373
+ "https://github.com/Excel-DNA/ExcelDna",
374
+ "https://github.com/Excel-DNA/IntelliSense",
375
+ "https://github.com/Excel-DNA/Registration"
376
+ ],
369
377
  "expo": "https://github.com/expo/expo",
370
378
  "fabric-chaincode-node": "https://github.com/hyperledger/fabric-chaincode-node",
371
379
  "fabric8-kubernetes-client": "https://github.com/fabric8io/kubernetes-client",
@@ -23,7 +23,7 @@ const globalConfigOptionDefaults = {
23
23
  "detectHostRulesFromEnv": false,
24
24
  "dockerChildPrefix": "renovate_",
25
25
  "dockerMaxPages": 20,
26
- "dockerSidecarImage": "ghcr.io/renovatebot/base-image:13.155.0",
26
+ "dockerSidecarImage": "ghcr.io/renovatebot/base-image:13.157.0",
27
27
  "dockerUser": "12021",
28
28
  "executionTimeout": 15,
29
29
  "exitCodeForErrors": false,
@@ -1 +1 @@
1
- {"version":3,"file":"global-config-option-defaults.generated.js","names":[],"sources":["../lib/global-config-option-defaults.generated.ts"],"sourcesContent":["\nexport const globalConfigOptionDefaults: Record<string, unknown> = {\n \"allowCustomCrateGitRegistries\": false,\n \"allowedCommands\": [],\n \"allowedEnv\": [],\n \"allowedHeaders\": [\n \"X-*\"\n ],\n \"allowedUnsafeExecutions\": [],\n \"allowPlugins\": false,\n \"allowScripts\": false,\n \"allowShellExecutorForPostUpgradeCommands\": false,\n \"autodiscover\": false,\n \"bbUseDevelopmentBranch\": false,\n \"binarySource\": \"install\",\n \"cacheHardTtlMinutes\": 10080,\n \"cachePrivatePackages\": false,\n \"cacheTtlOverride\": {},\n \"checkedBranches\": [],\n \"configValidationError\": false,\n \"customEnvVariables\": {},\n \"deleteAdditionalConfigFile\": false,\n \"deleteConfigFile\": false,\n \"detectGlobalManagerConfig\": false,\n \"detectHostRulesFromEnv\": false,\n \"dockerChildPrefix\": \"renovate_\",\n \"dockerMaxPages\": 20,\n \"dockerSidecarImage\": \"ghcr.io/renovatebot/base-image:13.155.0\",\n \"dockerUser\": \"12021\",\n \"executionTimeout\": 15,\n \"exitCodeForErrors\": false,\n \"exposeAllEnv\": false,\n \"forceCli\": true,\n \"forkCreation\": true,\n \"githubTokenWarn\": true,\n \"gitNoVerify\": [\n \"commit\",\n \"push\"\n ],\n \"gitTimeout\": 0,\n \"gitUrl\": \"default\",\n \"goEnvFromHostRules\": false,\n \"httpCacheTtlDays\": 90,\n \"ignorePrAuthor\": false,\n \"includeMirrors\": false,\n \"inheritConfig\": false,\n \"inheritConfigFileName\": \"org-inherited-config.json\",\n \"inheritConfigRepoName\": \"{{parentOrg}}/renovate-config\",\n \"inheritConfigStrict\": false,\n \"inheritConfigTrusted\": false,\n \"internalHostAccess\": \"warn\",\n \"mergeConfidenceDatasources\": [\n \"go\",\n \"maven\",\n \"npm\",\n \"nuget\",\n \"packagist\",\n \"pypi\",\n \"rubygems\"\n ],\n \"mergeConfidenceEndpoint\": \"https://developer.mend.io/\",\n \"migratePresets\": {},\n \"onboardingBranch\": \"renovate/configure\",\n \"onboardingConfig\": {\n \"$schema\": \"https://docs.renovatebot.com/renovate-schema.json\"\n },\n \"onboardingConfigFileName\": \"renovate.json\",\n \"onboardingNoDeps\": \"auto\",\n \"onboardingPrTitle\": \"Configure Renovate\",\n \"onboardingRebaseCheckbox\": false,\n \"optimizeForDisabled\": false,\n \"persistRepoData\": false,\n \"platform\": \"github\",\n \"prCacheSyncMaxPages\": 100,\n \"prCommitsPerRunLimit\": 0,\n \"presetCachePersistence\": false,\n \"processEnv\": {},\n \"productLinks\": {\n \"documentation\": \"https://docs.renovatebot.com/\",\n \"help\": \"https://github.com/renovatebot/renovate/discussions\",\n \"homepage\": \"https://github.com/renovatebot/renovate\"\n },\n \"rebaseAllOpenBranches\": false,\n \"reportFormatting\": false,\n \"repositoryCache\": \"disabled\",\n \"repositoryCacheForceLocal\": false,\n \"repositoryCacheType\": \"local\",\n \"requireConfig\": \"required\",\n \"s3PathStyle\": false,\n \"secrets\": {},\n \"unicodeEmoji\": true,\n \"useCloudMetadataServices\": true,\n \"userAgent\": \"Renovate/{{renovateVersion}} (https://github.com/renovatebot/renovate)\",\n \"variables\": {}\n};\n"],"mappings":";AACA,MAAa,6BAAsD;CACjE,iCAAiC;CACjC,mBAAmB,CAAC;CACpB,cAAc,CAAC;CACf,kBAAkB,CAChB,KACF;CACA,2BAA2B,CAAC;CAC5B,gBAAgB;CAChB,gBAAgB;CAChB,4CAA4C;CAC5C,gBAAgB;CAChB,0BAA0B;CAC1B,gBAAgB;CAChB,uBAAuB;CACvB,wBAAwB;CACxB,oBAAoB,CAAC;CACrB,mBAAmB,CAAC;CACpB,yBAAyB;CACzB,sBAAsB,CAAC;CACvB,8BAA8B;CAC9B,oBAAoB;CACpB,6BAA6B;CAC7B,0BAA0B;CAC1B,qBAAqB;CACrB,kBAAkB;CAClB,sBAAsB;CACtB,cAAc;CACd,oBAAoB;CACpB,qBAAqB;CACrB,gBAAgB;CAChB,YAAY;CACZ,gBAAgB;CAChB,mBAAmB;CACnB,eAAe,CACb,UACA,MACF;CACA,cAAc;CACd,UAAU;CACV,sBAAsB;CACtB,oBAAoB;CACpB,kBAAkB;CAClB,kBAAkB;CAClB,iBAAiB;CACjB,yBAAyB;CACzB,yBAAyB;CACzB,uBAAuB;CACvB,wBAAwB;CACxB,sBAAsB;CACtB,8BAA8B;EAC5B;EACA;EACA;EACA;EACA;EACA;EACA;CACF;CACA,2BAA2B;CAC3B,kBAAkB,CAAC;CACnB,oBAAoB;CACpB,oBAAoB,EAClB,WAAW,oDACb;CACA,4BAA4B;CAC5B,oBAAoB;CACpB,qBAAqB;CACrB,4BAA4B;CAC5B,uBAAuB;CACvB,mBAAmB;CACnB,YAAY;CACZ,uBAAuB;CACvB,wBAAwB;CACxB,0BAA0B;CAC1B,cAAc,CAAC;CACf,gBAAgB;EACd,iBAAiB;EACjB,QAAQ;EACR,YAAY;CACd;CACA,yBAAyB;CACzB,oBAAoB;CACpB,mBAAmB;CACnB,6BAA6B;CAC7B,uBAAuB;CACvB,iBAAiB;CACjB,eAAe;CACf,WAAW,CAAC;CACZ,gBAAgB;CAChB,4BAA4B;CAC5B,aAAa;CACb,aAAa,CAAC;AAChB"}
1
+ {"version":3,"file":"global-config-option-defaults.generated.js","names":[],"sources":["../lib/global-config-option-defaults.generated.ts"],"sourcesContent":["\nexport const globalConfigOptionDefaults: Record<string, unknown> = {\n \"allowCustomCrateGitRegistries\": false,\n \"allowedCommands\": [],\n \"allowedEnv\": [],\n \"allowedHeaders\": [\n \"X-*\"\n ],\n \"allowedUnsafeExecutions\": [],\n \"allowPlugins\": false,\n \"allowScripts\": false,\n \"allowShellExecutorForPostUpgradeCommands\": false,\n \"autodiscover\": false,\n \"bbUseDevelopmentBranch\": false,\n \"binarySource\": \"install\",\n \"cacheHardTtlMinutes\": 10080,\n \"cachePrivatePackages\": false,\n \"cacheTtlOverride\": {},\n \"checkedBranches\": [],\n \"configValidationError\": false,\n \"customEnvVariables\": {},\n \"deleteAdditionalConfigFile\": false,\n \"deleteConfigFile\": false,\n \"detectGlobalManagerConfig\": false,\n \"detectHostRulesFromEnv\": false,\n \"dockerChildPrefix\": \"renovate_\",\n \"dockerMaxPages\": 20,\n \"dockerSidecarImage\": \"ghcr.io/renovatebot/base-image:13.157.0\",\n \"dockerUser\": \"12021\",\n \"executionTimeout\": 15,\n \"exitCodeForErrors\": false,\n \"exposeAllEnv\": false,\n \"forceCli\": true,\n \"forkCreation\": true,\n \"githubTokenWarn\": true,\n \"gitNoVerify\": [\n \"commit\",\n \"push\"\n ],\n \"gitTimeout\": 0,\n \"gitUrl\": \"default\",\n \"goEnvFromHostRules\": false,\n \"httpCacheTtlDays\": 90,\n \"ignorePrAuthor\": false,\n \"includeMirrors\": false,\n \"inheritConfig\": false,\n \"inheritConfigFileName\": \"org-inherited-config.json\",\n \"inheritConfigRepoName\": \"{{parentOrg}}/renovate-config\",\n \"inheritConfigStrict\": false,\n \"inheritConfigTrusted\": false,\n \"internalHostAccess\": \"warn\",\n \"mergeConfidenceDatasources\": [\n \"go\",\n \"maven\",\n \"npm\",\n \"nuget\",\n \"packagist\",\n \"pypi\",\n \"rubygems\"\n ],\n \"mergeConfidenceEndpoint\": \"https://developer.mend.io/\",\n \"migratePresets\": {},\n \"onboardingBranch\": \"renovate/configure\",\n \"onboardingConfig\": {\n \"$schema\": \"https://docs.renovatebot.com/renovate-schema.json\"\n },\n \"onboardingConfigFileName\": \"renovate.json\",\n \"onboardingNoDeps\": \"auto\",\n \"onboardingPrTitle\": \"Configure Renovate\",\n \"onboardingRebaseCheckbox\": false,\n \"optimizeForDisabled\": false,\n \"persistRepoData\": false,\n \"platform\": \"github\",\n \"prCacheSyncMaxPages\": 100,\n \"prCommitsPerRunLimit\": 0,\n \"presetCachePersistence\": false,\n \"processEnv\": {},\n \"productLinks\": {\n \"documentation\": \"https://docs.renovatebot.com/\",\n \"help\": \"https://github.com/renovatebot/renovate/discussions\",\n \"homepage\": \"https://github.com/renovatebot/renovate\"\n },\n \"rebaseAllOpenBranches\": false,\n \"reportFormatting\": false,\n \"repositoryCache\": \"disabled\",\n \"repositoryCacheForceLocal\": false,\n \"repositoryCacheType\": \"local\",\n \"requireConfig\": \"required\",\n \"s3PathStyle\": false,\n \"secrets\": {},\n \"unicodeEmoji\": true,\n \"useCloudMetadataServices\": true,\n \"userAgent\": \"Renovate/{{renovateVersion}} (https://github.com/renovatebot/renovate)\",\n \"variables\": {}\n};\n"],"mappings":";AACA,MAAa,6BAAsD;CACjE,iCAAiC;CACjC,mBAAmB,CAAC;CACpB,cAAc,CAAC;CACf,kBAAkB,CAChB,KACF;CACA,2BAA2B,CAAC;CAC5B,gBAAgB;CAChB,gBAAgB;CAChB,4CAA4C;CAC5C,gBAAgB;CAChB,0BAA0B;CAC1B,gBAAgB;CAChB,uBAAuB;CACvB,wBAAwB;CACxB,oBAAoB,CAAC;CACrB,mBAAmB,CAAC;CACpB,yBAAyB;CACzB,sBAAsB,CAAC;CACvB,8BAA8B;CAC9B,oBAAoB;CACpB,6BAA6B;CAC7B,0BAA0B;CAC1B,qBAAqB;CACrB,kBAAkB;CAClB,sBAAsB;CACtB,cAAc;CACd,oBAAoB;CACpB,qBAAqB;CACrB,gBAAgB;CAChB,YAAY;CACZ,gBAAgB;CAChB,mBAAmB;CACnB,eAAe,CACb,UACA,MACF;CACA,cAAc;CACd,UAAU;CACV,sBAAsB;CACtB,oBAAoB;CACpB,kBAAkB;CAClB,kBAAkB;CAClB,iBAAiB;CACjB,yBAAyB;CACzB,yBAAyB;CACzB,uBAAuB;CACvB,wBAAwB;CACxB,sBAAsB;CACtB,8BAA8B;EAC5B;EACA;EACA;EACA;EACA;EACA;EACA;CACF;CACA,2BAA2B;CAC3B,kBAAkB,CAAC;CACnB,oBAAoB;CACpB,oBAAoB,EAClB,WAAW,oDACb;CACA,4BAA4B;CAC5B,oBAAoB;CACpB,qBAAqB;CACrB,4BAA4B;CAC5B,uBAAuB;CACvB,mBAAmB;CACnB,YAAY;CACZ,uBAAuB;CACvB,wBAAwB;CACxB,0BAA0B;CAC1B,cAAc,CAAC;CACf,gBAAgB;EACd,iBAAiB;EACjB,QAAQ;EACR,YAAY;CACd;CACA,yBAAyB;CACzB,oBAAoB;CACpB,mBAAmB;CACnB,6BAA6B;CAC7B,uBAAuB;CACvB,iBAAiB;CACjB,eAAe;CACf,WAAW,CAAC;CACZ,gBAAgB;CAChB,4BAA4B;CAC5B,aAAa;CACb,aAAa,CAAC;AAChB"}
@@ -1,6 +1,7 @@
1
1
  import { pkg } from "../expose.js";
2
2
  import { GetDatasourceReleasesSpanProcessor } from "../modules/datasource/span-processor.js";
3
3
  import { GitOperationSpanProcessor } from "../util/git/span-processor.js";
4
+ import { isNotFound, isUnauthorized } from "../util/http/status.js";
4
5
  import { getResourceDetectors } from "./detectors.js";
5
6
  import { FileSpanExporter } from "./file-exporter.js";
6
7
  import { getFileExporterPath, getOtlpProtocol, isFileExporterEnabled, isTraceDebuggingEnabled, isTraceSendingEnabled, isTracingEnabled, massageThrowable } from "./utils.js";
@@ -61,8 +62,8 @@ function init() {
61
62
  new HttpInstrumentation({
62
63
  /* v8 ignore start -- not easily testable */
63
64
  applyCustomAttributesOnSpan: (span, request, response) => {
64
- if (request instanceof ClientRequest && request.host === `api.github.com` && request.path.endsWith(`/protection`) && response.statusCode === 404) span.setStatus({ code: SpanStatusCode.OK });
65
- else if (request instanceof ClientRequest && request.path === "/v2/" && request.method === "GET" && !request.getHeader("authorization") && response instanceof ServerResponse && response.getHeader("www-authenticate") && response.getHeader("docker-distribution-api-version") && response.statusCode === 401) span.setStatus({ code: SpanStatusCode.OK });
65
+ if (request instanceof ClientRequest && request.host === `api.github.com` && request.path.endsWith(`/protection`) && isNotFound(response)) span.setStatus({ code: SpanStatusCode.OK });
66
+ else if (request instanceof ClientRequest && request.path === "/v2/" && request.method === "GET" && !request.getHeader("authorization") && response instanceof ServerResponse && response.getHeader("www-authenticate") && response.getHeader("docker-distribution-api-version") && isUnauthorized(response)) span.setStatus({ code: SpanStatusCode.OK });
66
67
  } }),
67
68
  new BunyanInstrumentation(),
68
69
  new RedisInstrumentation()
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["OTLPTraceExporterGrpc","OTLPTraceExporterProto","OTLPTraceExporterHttp","SdkTracerProvider"],"sources":["../../lib/instrumentation/index.ts"],"sourcesContent":["import { ClientRequest, ServerResponse } from 'node:http';\nimport type { Context, Span, Tracer, TracerProvider } from '@opentelemetry/api';\nimport * as api from '@opentelemetry/api';\nimport { ProxyTracerProvider, SpanStatusCode } from '@opentelemetry/api';\nimport { AsyncLocalStorageContextManager } from '@opentelemetry/context-async-hooks';\nimport {\n CompositePropagator,\n W3CBaggagePropagator,\n W3CTraceContextPropagator,\n} from '@opentelemetry/core';\nimport { OTLPTraceExporter as OTLPTraceExporterGrpc } from '@opentelemetry/exporter-trace-otlp-grpc';\nimport { OTLPTraceExporter as OTLPTraceExporterHttp } from '@opentelemetry/exporter-trace-otlp-http';\nimport { OTLPTraceExporter as OTLPTraceExporterProto } from '@opentelemetry/exporter-trace-otlp-proto';\nimport type { Instrumentation } from '@opentelemetry/instrumentation';\nimport { registerInstrumentations } from '@opentelemetry/instrumentation';\nimport { BunyanInstrumentation } from '@opentelemetry/instrumentation-bunyan';\nimport { HttpInstrumentation } from '@opentelemetry/instrumentation-http';\nimport { RedisInstrumentation } from '@opentelemetry/instrumentation-redis';\nimport {\n detectResources,\n resourceFromAttributes,\n} from '@opentelemetry/resources';\nimport {\n BatchSpanProcessor,\n ConsoleSpanExporter,\n TracerProvider as SdkTracerProvider,\n SimpleSpanProcessor,\n type SpanExporter,\n type SpanProcessor,\n} from '@opentelemetry/sdk-trace';\nimport {\n ATTR_SERVICE_NAME,\n ATTR_SERVICE_VERSION,\n} from '@opentelemetry/semantic-conventions';\nimport { isPromise } from '@sindresorhus/is';\nimport { pkg } from '../expose.ts';\nimport { GetDatasourceReleasesSpanProcessor } from '../modules/datasource/span-processor.ts';\nimport { GitOperationSpanProcessor } from '../util/git/span-processor.ts';\nimport { getResourceDetectors } from './detectors.ts';\nimport { FileSpanExporter } from './file-exporter.ts';\nimport type { RenovateSpanOptions } from './types.ts';\nimport {\n getFileExporterPath,\n getOtlpProtocol,\n isFileExporterEnabled,\n isTraceDebuggingEnabled,\n isTraceSendingEnabled,\n isTracingEnabled,\n massageThrowable,\n} from './utils.ts';\n\nlet instrumentations: Instrumentation[] = [];\n\nfunction createOtlpExporter(): SpanExporter {\n const protocol = getOtlpProtocol();\n if (protocol === 'grpc') {\n return new OTLPTraceExporterGrpc();\n }\n if (protocol === 'http/protobuf') {\n return new OTLPTraceExporterProto();\n }\n return new OTLPTraceExporterHttp();\n}\n\nfunction registerProvider(provider: SdkTracerProvider): void {\n const contextManager = new AsyncLocalStorageContextManager();\n contextManager.enable();\n api.context.setGlobalContextManager(contextManager);\n api.propagation.setGlobalPropagator(\n new CompositePropagator({\n propagators: [\n new W3CTraceContextPropagator(),\n new W3CBaggagePropagator(),\n ],\n }),\n );\n api.trace.setGlobalTracerProvider(provider);\n}\n\nexport function init(): void {\n const spanProcessors: SpanProcessor[] = [\n new GitOperationSpanProcessor(),\n new GetDatasourceReleasesSpanProcessor(),\n ];\n\n if (!isTracingEnabled()) {\n registerProvider(new SdkTracerProvider({ spanProcessors }));\n return;\n }\n\n // v8 ignore if -- TODO add tests\n if (process.env.OTEL_LOG_LEVEL) {\n api.diag.setLogger(\n new api.DiagConsoleLogger(),\n api.DiagLogLevel[\n process.env.OTEL_LOG_LEVEL.toUpperCase() as keyof typeof api.DiagLogLevel\n ],\n );\n }\n\n // add processors\n if (isTraceDebuggingEnabled()) {\n spanProcessors.push(\n new SimpleSpanProcessor({ exporter: new ConsoleSpanExporter() }),\n );\n }\n\n // OTEL specification environment variable\n if (isTraceSendingEnabled()) {\n spanProcessors.push(\n new BatchSpanProcessor({ exporter: createOtlpExporter() }),\n );\n }\n\n if (isFileExporterEnabled()) {\n spanProcessors.push(\n new BatchSpanProcessor({\n exporter: new FileSpanExporter(getFileExporterPath()),\n }),\n );\n }\n\n const env = process.env; // don't use getEnv() here to avoid circular dependency with env variables used in the resource detectors\n const baseResource = resourceFromAttributes({\n // https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/resource/semantic_conventions/README.md#semantic-attributes-with-sdk-provided-default-value\n [ATTR_SERVICE_NAME]: env.OTEL_SERVICE_NAME ?? 'renovate',\n // https://github.com/open-telemetry/opentelemetry-js/tree/main/semantic-conventions#unstable-semconv\n // https://github.com/open-telemetry/opentelemetry-js/blob/e9d3c71918635d490b6a9ac9f8259265b38394d0/semantic-conventions/src/experimental_attributes.ts#L7688\n ['service.namespace']: env.OTEL_SERVICE_NAMESPACE ?? 'renovatebot.com',\n [ATTR_SERVICE_VERSION]: env.OTEL_SERVICE_VERSION ?? pkg.version,\n });\n\n const detectedResource = detectResources({\n detectors: getResourceDetectors(env),\n });\n\n registerProvider(\n new SdkTracerProvider({\n resource: baseResource.merge(detectedResource),\n spanProcessors,\n }),\n );\n\n instrumentations = [\n new HttpInstrumentation({\n /* v8 ignore start -- not easily testable */\n applyCustomAttributesOnSpan: (span, request, response) => {\n // ignore 404 errors when the branch protection of Github could not be found. This is expected if no rules are configured\n if (\n request instanceof ClientRequest &&\n request.host === `api.github.com` &&\n request.path.endsWith(`/protection`) &&\n response.statusCode === 404\n ) {\n span.setStatus({ code: SpanStatusCode.OK });\n } else if (\n request instanceof ClientRequest &&\n request.path === '/v2/' &&\n request.method === 'GET' &&\n !request.getHeader('authorization') &&\n response instanceof ServerResponse &&\n response.getHeader('www-authenticate') &&\n response.getHeader('docker-distribution-api-version') &&\n response.statusCode === 401\n ) {\n // Docker API test expects 401 with `www-authenticate` header when registry requires authentication, so ignore this error\n span.setStatus({ code: SpanStatusCode.OK });\n }\n },\n /* v8 ignore stop -- not easily testable */\n }),\n new BunyanInstrumentation(),\n new RedisInstrumentation(),\n ];\n registerInstrumentations({\n instrumentations,\n });\n}\n\n// https://github.com/open-telemetry/opentelemetry-js-api/issues/34\n/* v8 ignore next -- not easily testable */\nexport async function shutdown(): Promise<void> {\n const traceProvider = getTracerProvider();\n if (traceProvider instanceof SdkTracerProvider) {\n await traceProvider.shutdown();\n } else if (traceProvider instanceof ProxyTracerProvider) {\n const delegateProvider = traceProvider.getDelegate();\n if (delegateProvider instanceof SdkTracerProvider) {\n await delegateProvider.shutdown();\n }\n }\n}\n\nexport function disableInstrumentations(): void {\n for (const instrumentation of instrumentations) {\n instrumentation.disable();\n }\n}\n\nexport function getTracerProvider(): TracerProvider {\n return api.trace.getTracerProvider();\n}\n\nfunction getTracer(): Tracer {\n return getTracerProvider().getTracer('renovate');\n}\n\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions,\n context: Context,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions = {},\n context: Context = api.context.active(),\n): ReturnType<F> {\n return getTracer().startActiveSpan(name, options, context, (span: Span) => {\n try {\n const ret = fn();\n if (isPromise(ret)) {\n return ret\n .catch((e) => {\n span.recordException(e);\n span.setStatus({\n code: SpanStatusCode.ERROR,\n message: massageThrowable(e),\n });\n throw e;\n })\n .finally(() => span.end()) as ReturnType<F>;\n }\n span.end();\n return ret;\n } catch (e) {\n span.recordException(e);\n span.setStatus({\n code: SpanStatusCode.ERROR,\n message: massageThrowable(e),\n });\n span.end();\n throw e;\n }\n });\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","names":["OTLPTraceExporterGrpc","OTLPTraceExporterProto","OTLPTraceExporterHttp","SdkTracerProvider"],"sources":["../../lib/instrumentation/index.ts"],"sourcesContent":["import { ClientRequest, ServerResponse } from 'node:http';\nimport type { Context, Span, Tracer, TracerProvider } from '@opentelemetry/api';\nimport * as api from '@opentelemetry/api';\nimport { ProxyTracerProvider, SpanStatusCode } from '@opentelemetry/api';\nimport { AsyncLocalStorageContextManager } from '@opentelemetry/context-async-hooks';\nimport {\n CompositePropagator,\n W3CBaggagePropagator,\n W3CTraceContextPropagator,\n} from '@opentelemetry/core';\nimport { OTLPTraceExporter as OTLPTraceExporterGrpc } from '@opentelemetry/exporter-trace-otlp-grpc';\nimport { OTLPTraceExporter as OTLPTraceExporterHttp } from '@opentelemetry/exporter-trace-otlp-http';\nimport { OTLPTraceExporter as OTLPTraceExporterProto } from '@opentelemetry/exporter-trace-otlp-proto';\nimport type { Instrumentation } from '@opentelemetry/instrumentation';\nimport { registerInstrumentations } from '@opentelemetry/instrumentation';\nimport { BunyanInstrumentation } from '@opentelemetry/instrumentation-bunyan';\nimport { HttpInstrumentation } from '@opentelemetry/instrumentation-http';\nimport { RedisInstrumentation } from '@opentelemetry/instrumentation-redis';\nimport {\n detectResources,\n resourceFromAttributes,\n} from '@opentelemetry/resources';\nimport {\n BatchSpanProcessor,\n ConsoleSpanExporter,\n TracerProvider as SdkTracerProvider,\n SimpleSpanProcessor,\n type SpanExporter,\n type SpanProcessor,\n} from '@opentelemetry/sdk-trace';\nimport {\n ATTR_SERVICE_NAME,\n ATTR_SERVICE_VERSION,\n} from '@opentelemetry/semantic-conventions';\nimport { isPromise } from '@sindresorhus/is';\nimport { pkg } from '../expose.ts';\nimport { GetDatasourceReleasesSpanProcessor } from '../modules/datasource/span-processor.ts';\nimport { GitOperationSpanProcessor } from '../util/git/span-processor.ts';\nimport { isNotFound, isUnauthorized } from '../util/http/status.ts';\nimport { getResourceDetectors } from './detectors.ts';\nimport { FileSpanExporter } from './file-exporter.ts';\nimport type { RenovateSpanOptions } from './types.ts';\nimport {\n getFileExporterPath,\n getOtlpProtocol,\n isFileExporterEnabled,\n isTraceDebuggingEnabled,\n isTraceSendingEnabled,\n isTracingEnabled,\n massageThrowable,\n} from './utils.ts';\n\nlet instrumentations: Instrumentation[] = [];\n\nfunction createOtlpExporter(): SpanExporter {\n const protocol = getOtlpProtocol();\n if (protocol === 'grpc') {\n return new OTLPTraceExporterGrpc();\n }\n if (protocol === 'http/protobuf') {\n return new OTLPTraceExporterProto();\n }\n return new OTLPTraceExporterHttp();\n}\n\nfunction registerProvider(provider: SdkTracerProvider): void {\n const contextManager = new AsyncLocalStorageContextManager();\n contextManager.enable();\n api.context.setGlobalContextManager(contextManager);\n api.propagation.setGlobalPropagator(\n new CompositePropagator({\n propagators: [\n new W3CTraceContextPropagator(),\n new W3CBaggagePropagator(),\n ],\n }),\n );\n api.trace.setGlobalTracerProvider(provider);\n}\n\nexport function init(): void {\n const spanProcessors: SpanProcessor[] = [\n new GitOperationSpanProcessor(),\n new GetDatasourceReleasesSpanProcessor(),\n ];\n\n if (!isTracingEnabled()) {\n registerProvider(new SdkTracerProvider({ spanProcessors }));\n return;\n }\n\n // v8 ignore if -- TODO add tests\n if (process.env.OTEL_LOG_LEVEL) {\n api.diag.setLogger(\n new api.DiagConsoleLogger(),\n api.DiagLogLevel[\n process.env.OTEL_LOG_LEVEL.toUpperCase() as keyof typeof api.DiagLogLevel\n ],\n );\n }\n\n // add processors\n if (isTraceDebuggingEnabled()) {\n spanProcessors.push(\n new SimpleSpanProcessor({ exporter: new ConsoleSpanExporter() }),\n );\n }\n\n // OTEL specification environment variable\n if (isTraceSendingEnabled()) {\n spanProcessors.push(\n new BatchSpanProcessor({ exporter: createOtlpExporter() }),\n );\n }\n\n if (isFileExporterEnabled()) {\n spanProcessors.push(\n new BatchSpanProcessor({\n exporter: new FileSpanExporter(getFileExporterPath()),\n }),\n );\n }\n\n const env = process.env; // don't use getEnv() here to avoid circular dependency with env variables used in the resource detectors\n const baseResource = resourceFromAttributes({\n // https://github.com/open-telemetry/opentelemetry-specification/blob/main/specification/resource/semantic_conventions/README.md#semantic-attributes-with-sdk-provided-default-value\n [ATTR_SERVICE_NAME]: env.OTEL_SERVICE_NAME ?? 'renovate',\n // https://github.com/open-telemetry/opentelemetry-js/tree/main/semantic-conventions#unstable-semconv\n // https://github.com/open-telemetry/opentelemetry-js/blob/e9d3c71918635d490b6a9ac9f8259265b38394d0/semantic-conventions/src/experimental_attributes.ts#L7688\n ['service.namespace']: env.OTEL_SERVICE_NAMESPACE ?? 'renovatebot.com',\n [ATTR_SERVICE_VERSION]: env.OTEL_SERVICE_VERSION ?? pkg.version,\n });\n\n const detectedResource = detectResources({\n detectors: getResourceDetectors(env),\n });\n\n registerProvider(\n new SdkTracerProvider({\n resource: baseResource.merge(detectedResource),\n spanProcessors,\n }),\n );\n\n instrumentations = [\n new HttpInstrumentation({\n /* v8 ignore start -- not easily testable */\n applyCustomAttributesOnSpan: (span, request, response) => {\n // ignore 404 errors when the branch protection of Github could not be found. This is expected if no rules are configured\n if (\n request instanceof ClientRequest &&\n request.host === `api.github.com` &&\n request.path.endsWith(`/protection`) &&\n isNotFound(response)\n ) {\n span.setStatus({ code: SpanStatusCode.OK });\n } else if (\n request instanceof ClientRequest &&\n request.path === '/v2/' &&\n request.method === 'GET' &&\n !request.getHeader('authorization') &&\n response instanceof ServerResponse &&\n response.getHeader('www-authenticate') &&\n response.getHeader('docker-distribution-api-version') &&\n isUnauthorized(response)\n ) {\n // Docker API test expects 401 with `www-authenticate` header when registry requires authentication, so ignore this error\n span.setStatus({ code: SpanStatusCode.OK });\n }\n },\n /* v8 ignore stop -- not easily testable */\n }),\n new BunyanInstrumentation(),\n new RedisInstrumentation(),\n ];\n registerInstrumentations({\n instrumentations,\n });\n}\n\n// https://github.com/open-telemetry/opentelemetry-js-api/issues/34\n/* v8 ignore next -- not easily testable */\nexport async function shutdown(): Promise<void> {\n const traceProvider = getTracerProvider();\n if (traceProvider instanceof SdkTracerProvider) {\n await traceProvider.shutdown();\n } else if (traceProvider instanceof ProxyTracerProvider) {\n const delegateProvider = traceProvider.getDelegate();\n if (delegateProvider instanceof SdkTracerProvider) {\n await delegateProvider.shutdown();\n }\n }\n}\n\nexport function disableInstrumentations(): void {\n for (const instrumentation of instrumentations) {\n instrumentation.disable();\n }\n}\n\nexport function getTracerProvider(): TracerProvider {\n return api.trace.getTracerProvider();\n}\n\nfunction getTracer(): Tracer {\n return getTracerProvider().getTracer('renovate');\n}\n\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions,\n context: Context,\n): ReturnType<F>;\nexport function instrument<F extends () => ReturnType<F>>(\n name: string,\n fn: F,\n options: RenovateSpanOptions = {},\n context: Context = api.context.active(),\n): ReturnType<F> {\n return getTracer().startActiveSpan(name, options, context, (span: Span) => {\n try {\n const ret = fn();\n if (isPromise(ret)) {\n return ret\n .catch((e) => {\n span.recordException(e);\n span.setStatus({\n code: SpanStatusCode.ERROR,\n message: massageThrowable(e),\n });\n throw e;\n })\n .finally(() => span.end()) as ReturnType<F>;\n }\n span.end();\n return ret;\n } catch (e) {\n span.recordException(e);\n span.setStatus({\n code: SpanStatusCode.ERROR,\n message: massageThrowable(e),\n });\n span.end();\n throw e;\n }\n });\n}\n"],"mappings":"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"}
@@ -85,14 +85,15 @@ function createLogger(stdoutLevel, problems) {
85
85
  * @returns returns the logLevel when the logLevelToCheck is valid or the defaultLevel passed as argument when it is undefined. Else it stops execution.
86
86
  */
87
87
  function validateLogLevel(logLevelToCheck, defaultLevel) {
88
- if (isUndefined(logLevelToCheck) || isString(logLevelToCheck) && [
88
+ const isAllowedString = isString(logLevelToCheck) && [
89
89
  "trace",
90
90
  "debug",
91
91
  "info",
92
92
  "warn",
93
93
  "error",
94
94
  "fatal"
95
- ].includes(logLevelToCheck)) return logLevelToCheck ?? defaultLevel;
95
+ ].includes(logLevelToCheck);
96
+ if (isUndefined(logLevelToCheck) || isAllowedString) return logLevelToCheck ?? defaultLevel;
96
97
  bunyan().createLogger({
97
98
  name: "renovate",
98
99
  streams: [{
@@ -1 +1 @@
1
- {"version":3,"file":"bunyan.js","names":[],"sources":["../../lib/logger/bunyan.ts"],"sourcesContent":["import { isString, isTruthy, isUndefined } from '@sindresorhus/is';\nimport fs from 'fs-extra';\nimport upath from 'upath';\nimport { bunyan } from '../expose.ts';\nimport cmdSerializer from './cmd-serializer.ts';\nimport configSerializer from './config-serializer.ts';\nimport errSerializer from './err-serializer.ts';\nimport { PrettyStdoutStream, formatRecord } from './pretty-stdout.ts';\nimport type { ProblemStream } from './problem-stream.ts';\nimport type {\n BunyanLogLevel,\n BunyanLogger,\n BunyanRecord,\n BunyanStream,\n} from './types.ts';\nimport { getEnv } from './utils.ts';\nimport { withSanitizer } from './with-sanitizer.ts';\n\nexport function createDefaultStreams(\n stdoutLevel: BunyanLogLevel,\n problems: ProblemStream,\n logFile: string | undefined,\n): BunyanStream[] {\n const stdout: BunyanStream = {\n name: 'stdout',\n level: stdoutLevel,\n stream: process.stdout,\n };\n\n // v8 ignore else -- TODO: add test #40625\n if (getEnv('LOG_FORMAT') !== 'json') {\n const prettyStdOut = new PrettyStdoutStream();\n stdout.stream = prettyStdOut;\n stdout.type = 'raw';\n }\n\n const problemsStream: BunyanStream = {\n name: 'problems',\n level: 'warn',\n stream: problems as any,\n type: 'raw',\n };\n\n const logFileStream: BunyanStream | undefined = isString(logFile)\n ? createLogFileStream(logFile)\n : undefined;\n\n return [stdout, problemsStream, logFileStream].filter(isTruthy);\n}\n\nfunction createLogFileStream(logFile: string): BunyanStream {\n // Ensure log file directory exists\n const directoryName = upath.dirname(logFile);\n fs.ensureDirSync(directoryName);\n\n const logFileLevel = validateLogLevel(getEnv('LOG_FILE_LEVEL'), 'debug');\n\n // Sync writes avoid data loss when process.exit() is called before async streams drain.\n const fd = fs.openSync(logFile, 'a');\n\n if (getEnv('LOG_FILE_FORMAT') === 'pretty') {\n return {\n name: 'logfile',\n level: logFileLevel,\n type: 'raw',\n stream: {\n writable: true,\n write: (rec: unknown) => {\n fs.writeSync(fd, formatRecord(rec as BunyanRecord, false));\n },\n },\n };\n }\n\n return {\n name: 'logfile',\n level: logFileLevel,\n stream: {\n writable: true,\n write: (data: string) => {\n fs.writeSync(fd, data);\n },\n },\n } as BunyanStream;\n}\n\nfunction serializedSanitizedLogger(streams: BunyanStream[]): BunyanLogger {\n return bunyan().createLogger({\n name: 'renovate',\n serializers: {\n body: configSerializer,\n cmd: cmdSerializer,\n config: configSerializer,\n migratedConfig: configSerializer,\n originalConfig: configSerializer,\n presetConfig: configSerializer,\n oldConfig: configSerializer,\n newConfig: configSerializer,\n err: errSerializer,\n },\n streams: streams.map(withSanitizer),\n });\n}\n\nexport function createLogger(\n stdoutLevel: BunyanLogLevel,\n problems: ProblemStream,\n): BunyanLogger {\n const defaultStreams = createDefaultStreams(\n stdoutLevel,\n problems,\n getEnv('LOG_FILE'),\n );\n\n return serializedSanitizedLogger(defaultStreams);\n}\n/**\n * A function that terminates execution if the log level that was entered is\n * not a valid value for the Bunyan logger.\n * @param logLevelToCheck\n * @returns returns the logLevel when the logLevelToCheck is valid or the defaultLevel passed as argument when it is undefined. Else it stops execution.\n */\nexport function validateLogLevel(\n logLevelToCheck: string | undefined,\n defaultLevel: BunyanLogLevel,\n): BunyanLogLevel {\n const allowedValues: BunyanLogLevel[] = [\n 'trace',\n 'debug',\n 'info',\n 'warn',\n 'error',\n 'fatal',\n ];\n\n if (\n isUndefined(logLevelToCheck) ||\n (isString(logLevelToCheck) &&\n allowedValues.includes(logLevelToCheck as BunyanLogLevel))\n ) {\n // log level is in the allowed values or its undefined\n return (logLevelToCheck as BunyanLogLevel) ?? defaultLevel;\n }\n\n const logger = bunyan().createLogger({\n name: 'renovate',\n streams: [\n {\n level: 'fatal',\n stream: process.stdout,\n },\n ],\n });\n logger.fatal({ logLevel: logLevelToCheck }, 'Invalid log level');\n process.exit(1);\n}\n"],"mappings":";;;;;;;;;;;AAkBA,SAAgB,qBACd,aACA,UACA,SACgB;CAChB,MAAM,SAAuB;EAC3B,MAAM;EACN,OAAO;EACP,QAAQ,QAAQ;CAClB;;CAGA,IAAI,OAAO,YAAY,MAAM,QAAQ;EAEnC,OAAO,SAAS,IADS,mBACE;EAC3B,OAAO,OAAO;CAChB;CAaA,OAAO;EAAC;EAAQ;GAVd,MAAM;GACN,OAAO;GACP,QAAQ;GACR,MAAM;EAOqB;EAJmB,SAAS,OAAO,IAC5D,oBAAoB,OAAO,IAC3B,KAAA;CAEyC,CAAC,CAAC,OAAO,QAAQ;AAChE;AAEA,SAAS,oBAAoB,SAA+B;CAE1D,MAAM,gBAAgB,MAAM,QAAQ,OAAO;CAC3C,GAAG,cAAc,aAAa;CAE9B,MAAM,eAAe,iBAAiB,OAAO,gBAAgB,GAAG,OAAO;CAGvE,MAAM,KAAK,GAAG,SAAS,SAAS,GAAG;CAEnC,IAAI,OAAO,iBAAiB,MAAM,UAChC,OAAO;EACL,MAAM;EACN,OAAO;EACP,MAAM;EACN,QAAQ;GACN,UAAU;GACV,QAAQ,QAAiB;IACvB,GAAG,UAAU,IAAI,aAAa,KAAqB,KAAK,CAAC;GAC3D;EACF;CACF;CAGF,OAAO;EACL,MAAM;EACN,OAAO;EACP,QAAQ;GACN,UAAU;GACV,QAAQ,SAAiB;IACvB,GAAG,UAAU,IAAI,IAAI;GACvB;EACF;CACF;AACF;AAEA,SAAS,0BAA0B,SAAuC;CACxE,OAAO,OAAO,CAAC,CAAC,aAAa;EAC3B,MAAM;EACN,aAAa;GACX,MAAM;GACN,KAAK;GACL,QAAQ;GACR,gBAAgB;GAChB,gBAAgB;GAChB,cAAc;GACd,WAAW;GACX,WAAW;GACX,KAAK;EACP;EACA,SAAS,QAAQ,IAAI,aAAa;CACpC,CAAC;AACH;AAEA,SAAgB,aACd,aACA,UACc;CAOd,OAAO,0BANgB,qBACrB,aACA,UACA,OAAO,UAAU,CAG2B,CAAC;AACjD;;;;;;;AAOA,SAAgB,iBACd,iBACA,cACgB;CAUhB,IACE,YAAY,eAAe,KAC1B,SAAS,eAAe,KACvB;EAXF;EACA;EACA;EACA;EACA;EACA;CAMc,CAAC,CAAC,SAAS,eAAiC,GAG1D,OAAQ,mBAAsC;CAYhD,OATsB,CAAC,CAAC,aAAa;EACnC,MAAM;EACN,SAAS,CACP;GACE,OAAO;GACP,QAAQ,QAAQ;EAClB,CACF;CACF,CACK,CAAC,CAAC,MAAM,EAAE,UAAU,gBAAgB,GAAG,mBAAmB;CAC/D,QAAQ,KAAK,CAAC;AAChB"}
1
+ {"version":3,"file":"bunyan.js","names":[],"sources":["../../lib/logger/bunyan.ts"],"sourcesContent":["import { isString, isTruthy, isUndefined } from '@sindresorhus/is';\nimport fs from 'fs-extra';\nimport upath from 'upath';\nimport { bunyan } from '../expose.ts';\nimport cmdSerializer from './cmd-serializer.ts';\nimport configSerializer from './config-serializer.ts';\nimport errSerializer from './err-serializer.ts';\nimport { PrettyStdoutStream, formatRecord } from './pretty-stdout.ts';\nimport type { ProblemStream } from './problem-stream.ts';\nimport type {\n BunyanLogLevel,\n BunyanLogger,\n BunyanRecord,\n BunyanStream,\n} from './types.ts';\nimport { getEnv } from './utils.ts';\nimport { withSanitizer } from './with-sanitizer.ts';\n\nexport function createDefaultStreams(\n stdoutLevel: BunyanLogLevel,\n problems: ProblemStream,\n logFile: string | undefined,\n): BunyanStream[] {\n const stdout: BunyanStream = {\n name: 'stdout',\n level: stdoutLevel,\n stream: process.stdout,\n };\n\n // v8 ignore else -- TODO: add test #40625\n if (getEnv('LOG_FORMAT') !== 'json') {\n const prettyStdOut = new PrettyStdoutStream();\n stdout.stream = prettyStdOut;\n stdout.type = 'raw';\n }\n\n const problemsStream: BunyanStream = {\n name: 'problems',\n level: 'warn',\n stream: problems as any,\n type: 'raw',\n };\n\n const logFileStream: BunyanStream | undefined = isString(logFile)\n ? createLogFileStream(logFile)\n : undefined;\n\n return [stdout, problemsStream, logFileStream].filter(isTruthy);\n}\n\nfunction createLogFileStream(logFile: string): BunyanStream {\n // Ensure log file directory exists\n const directoryName = upath.dirname(logFile);\n fs.ensureDirSync(directoryName);\n\n const logFileLevel = validateLogLevel(getEnv('LOG_FILE_LEVEL'), 'debug');\n\n // Sync writes avoid data loss when process.exit() is called before async streams drain.\n const fd = fs.openSync(logFile, 'a');\n\n if (getEnv('LOG_FILE_FORMAT') === 'pretty') {\n return {\n name: 'logfile',\n level: logFileLevel,\n type: 'raw',\n stream: {\n writable: true,\n write: (rec: unknown) => {\n fs.writeSync(fd, formatRecord(rec as BunyanRecord, false));\n },\n },\n };\n }\n\n return {\n name: 'logfile',\n level: logFileLevel,\n stream: {\n writable: true,\n write: (data: string) => {\n fs.writeSync(fd, data);\n },\n },\n } as BunyanStream;\n}\n\nfunction serializedSanitizedLogger(streams: BunyanStream[]): BunyanLogger {\n return bunyan().createLogger({\n name: 'renovate',\n serializers: {\n body: configSerializer,\n cmd: cmdSerializer,\n config: configSerializer,\n migratedConfig: configSerializer,\n originalConfig: configSerializer,\n presetConfig: configSerializer,\n oldConfig: configSerializer,\n newConfig: configSerializer,\n err: errSerializer,\n },\n streams: streams.map(withSanitizer),\n });\n}\n\nexport function createLogger(\n stdoutLevel: BunyanLogLevel,\n problems: ProblemStream,\n): BunyanLogger {\n const defaultStreams = createDefaultStreams(\n stdoutLevel,\n problems,\n getEnv('LOG_FILE'),\n );\n\n return serializedSanitizedLogger(defaultStreams);\n}\n/**\n * A function that terminates execution if the log level that was entered is\n * not a valid value for the Bunyan logger.\n * @param logLevelToCheck\n * @returns returns the logLevel when the logLevelToCheck is valid or the defaultLevel passed as argument when it is undefined. Else it stops execution.\n */\nexport function validateLogLevel(\n logLevelToCheck: string | undefined,\n defaultLevel: BunyanLogLevel,\n): BunyanLogLevel {\n const allowedValues: BunyanLogLevel[] = [\n 'trace',\n 'debug',\n 'info',\n 'warn',\n 'error',\n 'fatal',\n ];\n\n const isAllowedString =\n isString(logLevelToCheck) &&\n allowedValues.includes(logLevelToCheck as BunyanLogLevel);\n if (isUndefined(logLevelToCheck) || isAllowedString) {\n // log level is in the allowed values or its undefined\n return (logLevelToCheck as BunyanLogLevel) ?? defaultLevel;\n }\n\n const logger = bunyan().createLogger({\n name: 'renovate',\n streams: [\n {\n level: 'fatal',\n stream: process.stdout,\n },\n ],\n });\n logger.fatal({ logLevel: logLevelToCheck }, 'Invalid log level');\n process.exit(1);\n}\n"],"mappings":";;;;;;;;;;;AAkBA,SAAgB,qBACd,aACA,UACA,SACgB;CAChB,MAAM,SAAuB;EAC3B,MAAM;EACN,OAAO;EACP,QAAQ,QAAQ;CAClB;;CAGA,IAAI,OAAO,YAAY,MAAM,QAAQ;EAEnC,OAAO,SAAS,IADS,mBACE;EAC3B,OAAO,OAAO;CAChB;CAaA,OAAO;EAAC;EAAQ;GAVd,MAAM;GACN,OAAO;GACP,QAAQ;GACR,MAAM;EAOqB;EAJmB,SAAS,OAAO,IAC5D,oBAAoB,OAAO,IAC3B,KAAA;CAEyC,CAAC,CAAC,OAAO,QAAQ;AAChE;AAEA,SAAS,oBAAoB,SAA+B;CAE1D,MAAM,gBAAgB,MAAM,QAAQ,OAAO;CAC3C,GAAG,cAAc,aAAa;CAE9B,MAAM,eAAe,iBAAiB,OAAO,gBAAgB,GAAG,OAAO;CAGvE,MAAM,KAAK,GAAG,SAAS,SAAS,GAAG;CAEnC,IAAI,OAAO,iBAAiB,MAAM,UAChC,OAAO;EACL,MAAM;EACN,OAAO;EACP,MAAM;EACN,QAAQ;GACN,UAAU;GACV,QAAQ,QAAiB;IACvB,GAAG,UAAU,IAAI,aAAa,KAAqB,KAAK,CAAC;GAC3D;EACF;CACF;CAGF,OAAO;EACL,MAAM;EACN,OAAO;EACP,QAAQ;GACN,UAAU;GACV,QAAQ,SAAiB;IACvB,GAAG,UAAU,IAAI,IAAI;GACvB;EACF;CACF;AACF;AAEA,SAAS,0BAA0B,SAAuC;CACxE,OAAO,OAAO,CAAC,CAAC,aAAa;EAC3B,MAAM;EACN,aAAa;GACX,MAAM;GACN,KAAK;GACL,QAAQ;GACR,gBAAgB;GAChB,gBAAgB;GAChB,cAAc;GACd,WAAW;GACX,WAAW;GACX,KAAK;EACP;EACA,SAAS,QAAQ,IAAI,aAAa;CACpC,CAAC;AACH;AAEA,SAAgB,aACd,aACA,UACc;CAOd,OAAO,0BANgB,qBACrB,aACA,UACA,OAAO,UAAU,CAG2B,CAAC;AACjD;;;;;;;AAOA,SAAgB,iBACd,iBACA,cACgB;CAUhB,MAAM,kBACJ,SAAS,eAAe,KACxB;EAVA;EACA;EACA;EACA;EACA;EACA;CAKY,CAAC,CAAC,SAAS,eAAiC;CAC1D,IAAI,YAAY,eAAe,KAAK,iBAElC,OAAQ,mBAAsC;CAYhD,OATsB,CAAC,CAAC,aAAa;EACnC,MAAM;EACN,SAAS,CACP;GACE,OAAO;GACP,QAAQ,QAAQ;EAClB,CACF;CACF,CACK,CAAC,CAAC,MAAM,EAAE,UAAU,gBAAgB,GAAG,mBAAmB;CAC/D,QAAQ,KAAK,CAAC;AAChB"}
@@ -59,7 +59,8 @@ function getDetails(rec) {
59
59
  const recFiltered = { ...rec };
60
60
  delete recFiltered.module;
61
61
  Object.keys(recFiltered).forEach((key) => {
62
- if (key === "logContext" || bunyanFields.includes(key) || metaFields.includes(key) && isString(recFiltered[key])) delete recFiltered[key];
62
+ const isMetaString = metaFields.includes(key) && isString(recFiltered[key]);
63
+ if (key === "logContext" || bunyanFields.includes(key) || isMetaString) delete recFiltered[key];
63
64
  });
64
65
  const remainingKeys = Object.keys(recFiltered);
65
66
  if (remainingKeys.length === 0) return "";
@@ -1 +1 @@
1
- {"version":3,"file":"pretty-stdout.js","names":["util"],"sources":["../../lib/logger/pretty-stdout.ts"],"sourcesContent":["// Code originally derived from https://github.com/hadfieldn/node-bunyan-prettystream but since heavily edited\n// Neither fork nor original repo appear to be maintained\n\nimport { Writable } from 'node:stream';\nimport * as util from 'node:util';\nimport { isNonEmptyObject, isPlainObject, isString } from '@sindresorhus/is';\nimport stringify from 'json-stringify-pretty-compact';\nimport { regEx } from '../util/regex.ts';\nimport type { BunyanRecord } from './types.ts';\n\nconst bunyanFields = [\n 'name',\n 'hostname',\n 'pid',\n 'level',\n 'v',\n 'time',\n 'msg',\n 'start_time',\n];\n/**\n * If a log contains any of these meta fields in the meta, promote them up to the log line, rather than rendering them with other meta fields.\n *\n * This only applies when these fields have a string value, otherwise they are treated as a regular meta field.\n */\nconst metaFields = [\n 'repository',\n 'baseBranch',\n 'packageFile',\n 'depType',\n 'dependency',\n 'branch',\n];\n\nconst levels: Record<number, string> = {\n 10: 'TRACE',\n 20: 'DEBUG',\n 30: ' INFO',\n 40: ' WARN',\n 50: 'ERROR',\n 60: 'FATAL',\n};\n\nconst colorizedLevels: Record<number, string> = {\n 10: util.styleText('gray', 'TRACE'),\n 20: util.styleText('blue', 'DEBUG'),\n 30: util.styleText('green', ' INFO'),\n 40: util.styleText('magenta', ' WARN'),\n 50: util.styleText('red', 'ERROR'),\n 60: util.styleText('bgRed', 'FATAL'),\n};\n\nexport function indent(str: string, leading = false): string {\n const prefix = leading ? ' ' : '';\n return prefix + str.split(regEx(/\\r?\\n/)).join('\\n ');\n}\n\nexport function getMeta(rec: BunyanRecord, colorize = true): string {\n if (!rec) {\n return '';\n }\n let res = rec.module ? ` [${rec.module}]` : ``;\n const filteredMeta = metaFields.filter((elem) => isString(rec[elem]));\n if (!filteredMeta.length) {\n return res;\n }\n const metaStr = filteredMeta\n .map((field) => `${field}=${String(rec[field])}`)\n .join(', ');\n res = ` (${metaStr})${res}`;\n return colorize ? util.styleText('gray', res) : res;\n}\n\nexport function getDetails(rec: BunyanRecord): string {\n if (!rec) {\n return '';\n }\n const recFiltered = { ...rec };\n delete recFiltered.module;\n Object.keys(recFiltered).forEach((key) => {\n if (\n key === 'logContext' ||\n bunyanFields.includes(key) ||\n (metaFields.includes(key) && isString(recFiltered[key]))\n ) {\n delete recFiltered[key];\n }\n });\n const remainingKeys = Object.keys(recFiltered);\n if (remainingKeys.length === 0) {\n return '';\n }\n\n // Handle err.stack specially for readable multi-line output\n const err = recFiltered.err;\n if (isPlainObject(err) && isString(err.stack)) {\n const { stack, ...errRest } = err;\n recFiltered.err = isNonEmptyObject(errRest) ? errRest : undefined;\n const parts: string[] = [];\n for (const key of remainingKeys) {\n if (key === 'err' && recFiltered.err === undefined) {\n continue;\n }\n parts.push(indent(`\"${key}\": ${stringify(recFiltered[key])}`, true));\n }\n const jsonPart = parts.join(',\\n');\n const stackPart = indent(stack, true);\n return jsonPart ? `${jsonPart}\\n${stackPart}\\n` : `${stackPart}\\n`;\n }\n\n return `${remainingKeys\n .map((key) => `${indent(`\"${key}\": ${stringify(recFiltered[key])}`, true)}`)\n .join(',\\n')}\\n`;\n}\n\nexport function formatRecord(rec: BunyanRecord, colorize = true): string {\n const level = colorize ? colorizedLevels[rec.level] : levels[rec.level];\n const msg = `${indent(rec.msg)}`;\n const meta = getMeta(rec, colorize);\n const details = getDetails(rec);\n return util.format('%s: %s%s\\n%s', level, msg, meta, details);\n}\n\nexport class PrettyStdoutStream extends Writable {\n constructor() {\n super({ objectMode: true });\n }\n\n override _write(\n data: BunyanRecord,\n _encoding: string,\n callback: (error?: Error | null) => void,\n ): void {\n process.stdout.write(formatRecord(data));\n callback();\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"pretty-stdout.js","names":["util"],"sources":["../../lib/logger/pretty-stdout.ts"],"sourcesContent":["// Code originally derived from https://github.com/hadfieldn/node-bunyan-prettystream but since heavily edited\n// Neither fork nor original repo appear to be maintained\n\nimport { Writable } from 'node:stream';\nimport * as util from 'node:util';\nimport { isNonEmptyObject, isPlainObject, isString } from '@sindresorhus/is';\nimport stringify from 'json-stringify-pretty-compact';\nimport { regEx } from '../util/regex.ts';\nimport type { BunyanRecord } from './types.ts';\n\nconst bunyanFields = [\n 'name',\n 'hostname',\n 'pid',\n 'level',\n 'v',\n 'time',\n 'msg',\n 'start_time',\n];\n/**\n * If a log contains any of these meta fields in the meta, promote them up to the log line, rather than rendering them with other meta fields.\n *\n * This only applies when these fields have a string value, otherwise they are treated as a regular meta field.\n */\nconst metaFields = [\n 'repository',\n 'baseBranch',\n 'packageFile',\n 'depType',\n 'dependency',\n 'branch',\n];\n\nconst levels: Record<number, string> = {\n 10: 'TRACE',\n 20: 'DEBUG',\n 30: ' INFO',\n 40: ' WARN',\n 50: 'ERROR',\n 60: 'FATAL',\n};\n\nconst colorizedLevels: Record<number, string> = {\n 10: util.styleText('gray', 'TRACE'),\n 20: util.styleText('blue', 'DEBUG'),\n 30: util.styleText('green', ' INFO'),\n 40: util.styleText('magenta', ' WARN'),\n 50: util.styleText('red', 'ERROR'),\n 60: util.styleText('bgRed', 'FATAL'),\n};\n\nexport function indent(str: string, leading = false): string {\n const prefix = leading ? ' ' : '';\n return prefix + str.split(regEx(/\\r?\\n/)).join('\\n ');\n}\n\nexport function getMeta(rec: BunyanRecord, colorize = true): string {\n if (!rec) {\n return '';\n }\n let res = rec.module ? ` [${rec.module}]` : ``;\n const filteredMeta = metaFields.filter((elem) => isString(rec[elem]));\n if (!filteredMeta.length) {\n return res;\n }\n const metaStr = filteredMeta\n .map((field) => `${field}=${String(rec[field])}`)\n .join(', ');\n res = ` (${metaStr})${res}`;\n return colorize ? util.styleText('gray', res) : res;\n}\n\nexport function getDetails(rec: BunyanRecord): string {\n if (!rec) {\n return '';\n }\n const recFiltered = { ...rec };\n delete recFiltered.module;\n Object.keys(recFiltered).forEach((key) => {\n const isMetaString = metaFields.includes(key) && isString(recFiltered[key]);\n if (key === 'logContext' || bunyanFields.includes(key) || isMetaString) {\n delete recFiltered[key];\n }\n });\n const remainingKeys = Object.keys(recFiltered);\n if (remainingKeys.length === 0) {\n return '';\n }\n\n // Handle err.stack specially for readable multi-line output\n const err = recFiltered.err;\n if (isPlainObject(err) && isString(err.stack)) {\n const { stack, ...errRest } = err;\n recFiltered.err = isNonEmptyObject(errRest) ? errRest : undefined;\n const parts: string[] = [];\n for (const key of remainingKeys) {\n if (key === 'err' && recFiltered.err === undefined) {\n continue;\n }\n parts.push(indent(`\"${key}\": ${stringify(recFiltered[key])}`, true));\n }\n const jsonPart = parts.join(',\\n');\n const stackPart = indent(stack, true);\n return jsonPart ? `${jsonPart}\\n${stackPart}\\n` : `${stackPart}\\n`;\n }\n\n return `${remainingKeys\n .map((key) => `${indent(`\"${key}\": ${stringify(recFiltered[key])}`, true)}`)\n .join(',\\n')}\\n`;\n}\n\nexport function formatRecord(rec: BunyanRecord, colorize = true): string {\n const level = colorize ? colorizedLevels[rec.level] : levels[rec.level];\n const msg = `${indent(rec.msg)}`;\n const meta = getMeta(rec, colorize);\n const details = getDetails(rec);\n return util.format('%s: %s%s\\n%s', level, msg, meta, details);\n}\n\nexport class PrettyStdoutStream extends Writable {\n constructor() {\n super({ objectMode: true });\n }\n\n override _write(\n data: BunyanRecord,\n _encoding: string,\n callback: (error?: Error | null) => void,\n ): void {\n process.stdout.write(formatRecord(data));\n callback();\n }\n}\n"],"mappings":"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"}
@@ -1,5 +1,6 @@
1
1
  import { logger } from "../../../logger/index.js";
2
2
  import { joinUrlParts } from "../../../util/url.js";
3
+ import { isRateLimitedOrServerError } from "../../../util/http/status.js";
3
4
  import { ExternalHostError } from "../../../types/errors/external-host-error.js";
4
5
  import { cachePathExists, createCacheWriteStream, ensureCacheDir, pipeline, rmCache } from "../../../util/fs/index.js";
5
6
  import "../../versioning/apk/index.js";
@@ -106,8 +107,7 @@ var ApkDatasource = class ApkDatasource extends Datasource {
106
107
  return groupPackagesByName(packages);
107
108
  } catch (err) {
108
109
  if (err instanceof RequestError) {
109
- const statusCode = err.response?.statusCode;
110
- if (statusCode === 429 || statusCode && statusCode >= 500) throw new ExternalHostError(err);
110
+ if (isRateLimitedOrServerError(err)) throw new ExternalHostError(err);
111
111
  throw err;
112
112
  }
113
113
  logger.warn({
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["fs.ensureCacheDir","fs.createCacheWriteStream","fs.pipeline","tarExtract","fs.cachePathExists","HttpError","fs.rmCache"],"sources":["../../../../lib/modules/datasource/apk/index.ts"],"sourcesContent":["import { randomUUID } from 'node:crypto';\nimport { isNonEmptyObject } from '@sindresorhus/is';\nimport { extract as tarExtract } from 'tar';\nimport upath from 'upath';\nimport { logger } from '../../../logger/index.ts';\nimport { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { withCache } from '../../../util/cache/package/with-cache.ts';\nimport * as fs from '../../../util/fs/index.ts';\nimport { HttpError } from '../../../util/http/index.ts';\nimport { asTimestamp } from '../../../util/timestamp.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { id as apkVersioning } from '../../versioning/apk/index.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { parseApkIndexFile } from './parser.ts';\nimport type { ApkPackage } from './types.ts';\nimport { constructComponentUrls } from './url.ts';\n\nexport const apkDatasourceId = 'apk';\n\nconst defaultConfig = {\n commitMessageTopic: '{{{depName}}} APK package',\n commitMessageExtra:\n 'to {{#if isMajor}}{{{prettyNewMajor}}}{{else}}{{{prettyNewVersion}}}{{/if}}',\n};\n\n/**\n * Groups packages by name so that a lookup does not scan the whole index.\n *\n * An index holds thousands of packages, and a name can appear more than once\n * when the component serves multiple versions of it.\n */\nfunction groupPackagesByName(\n packages: ApkPackage[],\n): Record<string, ApkPackage[]> {\n const packagesByName: Record<string, ApkPackage[]> = {};\n\n for (const pkg of packages) {\n packagesByName[pkg.name] ??= [];\n packagesByName[pkg.name].push(pkg);\n }\n\n return packagesByName;\n}\n\nexport class ApkDatasource extends Datasource {\n static readonly id = apkDatasourceId;\n\n override readonly defaultVersioning = apkVersioning;\n\n /**\n * Alpine APK repositories are laid out as\n * `{base}/{branch}/{component}/{arch}/APKINDEX.tar.gz`, and `/etc/apk/repositories`\n * holds one entry per component.\n *\n * For Renovate, the path segments are encoded as query parameters so that a single\n * registry URL can cover multiple components.\n *\n * The following query parameter is required:\n * - arch: e.g. x86_64, aarch64, armv7\n *\n * The following query parameters are optional, as repositories such as Wolfi serve\n * their index directly below the repository root:\n * - branch: latest-stable, v3.19, edge or any other Alpine branch\n * - components: comma separated list of components, e.g. main,community,testing\n */\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return [\n 'https://dl-cdn.alpinelinux.org/alpine?branch=latest-stable&components=main&arch=x86_64',\n ];\n }\n\n override readonly defaultConfig = defaultConfig;\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n\n override readonly registryStrategy = 'merge';\n\n override readonly releaseTimestampSupport = true;\n override readonly releaseTimestampNote =\n 'The release timestamp is determined from the `buildDate` field in the results.';\n\n constructor() {\n super(ApkDatasource.id);\n }\n\n /**\n * Gets all available packages from a single APK component, keyed by package name\n */\n private async _getPackages(\n componentUrl: string,\n ): Promise<Record<string, ApkPackage[]>> {\n logger.debug(`Fetching APK packages from ${componentUrl}`);\n\n const extractId = randomUUID();\n const cacheDir = await fs.ensureCacheDir(upath.join('apk', extractId));\n const tarFile = upath.join(cacheDir, 'APKINDEX.tar.gz');\n const extractedFile = upath.join(cacheDir, 'APKINDEX');\n\n try {\n const indexUrl = joinUrlParts(componentUrl, 'APKINDEX.tar.gz');\n logger.debug(`Attempting to download ${indexUrl}`);\n const readStream = this.http.stream(indexUrl);\n const writeStream = fs.createCacheWriteStream(tarFile);\n await fs.pipeline(readStream, writeStream);\n\n await tarExtract({\n file: tarFile,\n cwd: cacheDir,\n filter: (path) => upath.basename(path) === 'APKINDEX',\n });\n\n if (!(await fs.cachePathExists(extractedFile))) {\n logger.warn({ componentUrl }, 'APKINDEX file not found in tar archive');\n return {};\n }\n\n logger.debug('Successfully extracted APKINDEX content');\n\n let packages: ApkPackage[] = [];\n try {\n packages = await parseApkIndexFile(extractedFile);\n } catch (err) {\n logger.warn({ componentUrl, err }, 'Error parsing APK index file');\n return {};\n }\n\n logger.debug(\n { componentUrl, packageCount: packages.length },\n 'Successfully parsed APK index',\n );\n\n return groupPackagesByName(packages);\n } catch (err) {\n if (err instanceof HttpError) {\n const statusCode = err.response?.statusCode;\n if (statusCode === 429 || (statusCode && statusCode >= 500)) {\n throw new ExternalHostError(err);\n }\n // The caller logs the failure once for the component it was skipping\n throw err;\n }\n\n logger.warn(\n { componentUrl, err },\n 'Error extracting APK index from tar.gz',\n );\n return {};\n } finally {\n await fs.rmCache(cacheDir);\n }\n }\n\n private getPackages(\n componentUrl: string,\n ): Promise<Record<string, ApkPackage[]>> {\n return withCache(\n {\n namespace: `datasource-${ApkDatasource.id}`,\n key: componentUrl,\n ttlMinutes: 60,\n fallback: true,\n },\n async (ctx) => {\n const packages = await this._getPackages(componentUrl);\n ctx.cacheable = isNonEmptyObject(packages);\n return packages;\n },\n );\n }\n\n /**\n * Gets releases for a specific package from APK repositories\n */\n async getReleases({\n packageName,\n registryUrl,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n /* v8 ignore if -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n logger.debug(`Getting APK releases for ${packageName} from ${registryUrl}`);\n\n const componentUrls = constructComponentUrls(registryUrl);\n let result: ReleaseResult | null = null;\n // A package can be served by more than one component, so the same version\n // must not be reported twice\n const seenVersions = new Set<string>();\n\n for (const componentUrl of componentUrls) {\n try {\n const packages = await this.getPackages(componentUrl);\n const matchingPackages = packages[packageName];\n\n if (!matchingPackages) {\n logger.debug(\n { packageName, componentUrl },\n 'No matching packages found',\n );\n continue;\n }\n\n const releases: Release[] = [];\n for (const pkg of matchingPackages) {\n if (seenVersions.has(pkg.version)) {\n continue;\n }\n seenVersions.add(pkg.version);\n releases.push({\n version: pkg.version,\n releaseTimestamp: pkg.buildDate\n ? asTimestamp(pkg.buildDate * 1000)\n : undefined,\n });\n }\n\n logger.trace(\n {\n packageName,\n componentUrl,\n releaseCount: releases.length,\n releases,\n },\n 'Found APK releases',\n );\n\n result ??= { releases: [], registryUrl };\n result.homepage ??= matchingPackages.find((pkg) => pkg.url)?.url;\n result.releases.push(...releases);\n } catch (err) {\n if (err instanceof ExternalHostError) {\n throw err;\n }\n logger.debug(\n { packageName, componentUrl, err },\n 'Skipping APK component due to an error',\n );\n }\n }\n\n return result;\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"index.js","names":["fs.ensureCacheDir","fs.createCacheWriteStream","fs.pipeline","tarExtract","fs.cachePathExists","HttpError","fs.rmCache"],"sources":["../../../../lib/modules/datasource/apk/index.ts"],"sourcesContent":["import { randomUUID } from 'node:crypto';\nimport { isNonEmptyObject } from '@sindresorhus/is';\nimport { extract as tarExtract } from 'tar';\nimport upath from 'upath';\nimport { logger } from '../../../logger/index.ts';\nimport { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { withCache } from '../../../util/cache/package/with-cache.ts';\nimport * as fs from '../../../util/fs/index.ts';\nimport { HttpError } from '../../../util/http/index.ts';\nimport { isRateLimitedOrServerError } from '../../../util/http/status.ts';\nimport { asTimestamp } from '../../../util/timestamp.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { id as apkVersioning } from '../../versioning/apk/index.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { parseApkIndexFile } from './parser.ts';\nimport type { ApkPackage } from './types.ts';\nimport { constructComponentUrls } from './url.ts';\n\nexport const apkDatasourceId = 'apk';\n\nconst defaultConfig = {\n commitMessageTopic: '{{{depName}}} APK package',\n commitMessageExtra:\n 'to {{#if isMajor}}{{{prettyNewMajor}}}{{else}}{{{prettyNewVersion}}}{{/if}}',\n};\n\n/**\n * Groups packages by name so that a lookup does not scan the whole index.\n *\n * An index holds thousands of packages, and a name can appear more than once\n * when the component serves multiple versions of it.\n */\nfunction groupPackagesByName(\n packages: ApkPackage[],\n): Record<string, ApkPackage[]> {\n const packagesByName: Record<string, ApkPackage[]> = {};\n\n for (const pkg of packages) {\n packagesByName[pkg.name] ??= [];\n packagesByName[pkg.name].push(pkg);\n }\n\n return packagesByName;\n}\n\nexport class ApkDatasource extends Datasource {\n static readonly id = apkDatasourceId;\n\n override readonly defaultVersioning = apkVersioning;\n\n /**\n * Alpine APK repositories are laid out as\n * `{base}/{branch}/{component}/{arch}/APKINDEX.tar.gz`, and `/etc/apk/repositories`\n * holds one entry per component.\n *\n * For Renovate, the path segments are encoded as query parameters so that a single\n * registry URL can cover multiple components.\n *\n * The following query parameter is required:\n * - arch: e.g. x86_64, aarch64, armv7\n *\n * The following query parameters are optional, as repositories such as Wolfi serve\n * their index directly below the repository root:\n * - branch: latest-stable, v3.19, edge or any other Alpine branch\n * - components: comma separated list of components, e.g. main,community,testing\n */\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return [\n 'https://dl-cdn.alpinelinux.org/alpine?branch=latest-stable&components=main&arch=x86_64',\n ];\n }\n\n override readonly defaultConfig = defaultConfig;\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n\n override readonly registryStrategy = 'merge';\n\n override readonly releaseTimestampSupport = true;\n override readonly releaseTimestampNote =\n 'The release timestamp is determined from the `buildDate` field in the results.';\n\n constructor() {\n super(ApkDatasource.id);\n }\n\n /**\n * Gets all available packages from a single APK component, keyed by package name\n */\n private async _getPackages(\n componentUrl: string,\n ): Promise<Record<string, ApkPackage[]>> {\n logger.debug(`Fetching APK packages from ${componentUrl}`);\n\n const extractId = randomUUID();\n const cacheDir = await fs.ensureCacheDir(upath.join('apk', extractId));\n const tarFile = upath.join(cacheDir, 'APKINDEX.tar.gz');\n const extractedFile = upath.join(cacheDir, 'APKINDEX');\n\n try {\n const indexUrl = joinUrlParts(componentUrl, 'APKINDEX.tar.gz');\n logger.debug(`Attempting to download ${indexUrl}`);\n const readStream = this.http.stream(indexUrl);\n const writeStream = fs.createCacheWriteStream(tarFile);\n await fs.pipeline(readStream, writeStream);\n\n await tarExtract({\n file: tarFile,\n cwd: cacheDir,\n filter: (path) => upath.basename(path) === 'APKINDEX',\n });\n\n if (!(await fs.cachePathExists(extractedFile))) {\n logger.warn({ componentUrl }, 'APKINDEX file not found in tar archive');\n return {};\n }\n\n logger.debug('Successfully extracted APKINDEX content');\n\n let packages: ApkPackage[] = [];\n try {\n packages = await parseApkIndexFile(extractedFile);\n } catch (err) {\n logger.warn({ componentUrl, err }, 'Error parsing APK index file');\n return {};\n }\n\n logger.debug(\n { componentUrl, packageCount: packages.length },\n 'Successfully parsed APK index',\n );\n\n return groupPackagesByName(packages);\n } catch (err) {\n if (err instanceof HttpError) {\n if (isRateLimitedOrServerError(err)) {\n throw new ExternalHostError(err);\n }\n // The caller logs the failure once for the component it was skipping\n throw err;\n }\n\n logger.warn(\n { componentUrl, err },\n 'Error extracting APK index from tar.gz',\n );\n return {};\n } finally {\n await fs.rmCache(cacheDir);\n }\n }\n\n private getPackages(\n componentUrl: string,\n ): Promise<Record<string, ApkPackage[]>> {\n return withCache(\n {\n namespace: `datasource-${ApkDatasource.id}`,\n key: componentUrl,\n ttlMinutes: 60,\n fallback: true,\n },\n async (ctx) => {\n const packages = await this._getPackages(componentUrl);\n ctx.cacheable = isNonEmptyObject(packages);\n return packages;\n },\n );\n }\n\n /**\n * Gets releases for a specific package from APK repositories\n */\n async getReleases({\n packageName,\n registryUrl,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n /* v8 ignore if -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n logger.debug(`Getting APK releases for ${packageName} from ${registryUrl}`);\n\n const componentUrls = constructComponentUrls(registryUrl);\n let result: ReleaseResult | null = null;\n // A package can be served by more than one component, so the same version\n // must not be reported twice\n const seenVersions = new Set<string>();\n\n for (const componentUrl of componentUrls) {\n try {\n const packages = await this.getPackages(componentUrl);\n const matchingPackages = packages[packageName];\n\n if (!matchingPackages) {\n logger.debug(\n { packageName, componentUrl },\n 'No matching packages found',\n );\n continue;\n }\n\n const releases: Release[] = [];\n for (const pkg of matchingPackages) {\n if (seenVersions.has(pkg.version)) {\n continue;\n }\n seenVersions.add(pkg.version);\n releases.push({\n version: pkg.version,\n releaseTimestamp: pkg.buildDate\n ? asTimestamp(pkg.buildDate * 1000)\n : undefined,\n });\n }\n\n logger.trace(\n {\n packageName,\n componentUrl,\n releaseCount: releases.length,\n releases,\n },\n 'Found APK releases',\n );\n\n result ??= { releases: [], registryUrl };\n result.homepage ??= matchingPackages.find((pkg) => pkg.url)?.url;\n result.releases.push(...releases);\n } catch (err) {\n if (err instanceof ExternalHostError) {\n throw err;\n }\n logger.debug(\n { packageName, componentUrl, err },\n 'Skipping APK component due to an error',\n );\n }\n }\n\n return result;\n }\n}\n"],"mappings":"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"}
@@ -2,8 +2,7 @@ import { regEx } from "../../../util/regex.js";
2
2
  import { logger } from "../../../logger/index.js";
3
3
  import { buildCacheKey } from "../../../util/cache/package/key.js";
4
4
  import { joinUrlParts } from "../../../util/url.js";
5
- import { RequestError } from "../../../util/http/got.js";
6
- import "../../../util/http/index.js";
5
+ import { isNotFound } from "../../../util/http/status.js";
7
6
  import { asTimestamp } from "../../../util/timestamp.js";
8
7
  import { Datasource } from "../datasource.js";
9
8
  import { parse } from "../../../util/html.js";
@@ -50,7 +49,7 @@ var ArtifactoryDatasource = class extends Datasource {
50
49
  packageName
51
50
  }, "artifactory: No versions found");
52
51
  } catch (err) {
53
- if (err instanceof RequestError && err.response?.statusCode === 404) {
52
+ if (isNotFound(err)) {
54
53
  logger.warn({
55
54
  registryUrl,
56
55
  packageName
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["HttpError"],"sources":["../../../../lib/modules/datasource/artifactory/index.ts"],"sourcesContent":["import { logger } from '../../../logger/index.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { parse } from '../../../util/html.ts';\nimport { HttpError } from '../../../util/http/index.ts';\nimport { regEx } from '../../../util/regex.ts';\nimport { asTimestamp } from '../../../util/timestamp.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { datasource } from './common.ts';\n\nexport class ArtifactoryDatasource extends Datasource {\n static readonly id = datasource;\n\n constructor() {\n super(datasource);\n }\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n\n override readonly registryStrategy = 'merge';\n\n override readonly releaseTimestampSupport = true;\n override readonly releaseTimestampNote =\n 'The release timestamp is determined from the date-like text, next to the version hyperlink tag in the results.';\n\n private async fetchReleases({\n packageName,\n registryUrl,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n if (!registryUrl) {\n logger.warn(\n { packageName },\n 'artifactory datasource requires custom registryUrl. Skipping datasource',\n );\n return null;\n }\n\n const url = joinUrlParts(registryUrl, packageName);\n\n const result: ReleaseResult = {\n releases: [],\n };\n try {\n const response = await this.http.getText(url);\n const body = parse(response.body, {\n blockTextElements: {\n script: true,\n noscript: true,\n style: true,\n },\n });\n const nodes = body.querySelectorAll('a');\n\n nodes\n .filter(\n // filter out hyperlink to navigate to parent folder\n (node) => node.innerHTML !== '../' && node.innerHTML !== '..',\n )\n .forEach(\n // extract version and published time for each node\n (node) => {\n const version: string = node.innerHTML.endsWith('/')\n ? node.innerHTML.slice(0, -1)\n : node.innerHTML;\n\n const releaseTimestamp = asTimestamp(\n node.nextSibling?.text?.trimStart()?.split(regEx(/\\s{2,}/))?.[0],\n );\n\n const thisRelease: Release = {\n version,\n releaseTimestamp,\n };\n\n result.releases.push(thisRelease);\n },\n );\n\n if (result.releases.length) {\n logger.trace(\n { registryUrl, packageName, versions: result.releases.length },\n 'artifactory: Found versions',\n );\n } else {\n logger.trace(\n { registryUrl, packageName },\n 'artifactory: No versions found',\n );\n }\n } catch (err) {\n if (err instanceof HttpError && err.response?.statusCode === 404) {\n logger.warn(\n { registryUrl, packageName },\n 'artifactory: `Not Found` error',\n );\n return null;\n }\n this.handleGenericErrors(err);\n }\n\n return result.releases.length ? result : null;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n return this.cached(\n {\n key: buildCacheKey(config.registryUrl, config.packageName),\n fallback: true,\n },\n () => this.fetchReleases(config),\n );\n }\n}\n"],"mappings":";;;;;;;;;;;AAWA,IAAa,wBAAb,cAA2C,WAAW;CACpD,OAAgB,KAAK;CAErB,cAAc;EACZ,MAAM,UAAU;CAClB;CAEA,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CAEA,mBAAqC;CAErC,0BAA4C;CAC5C,uBACE;CAEF,MAAc,cAAc,EAC1B,aACA,eACmD;EACnD,IAAI,CAAC,aAAa;GAChB,OAAO,KACL,EAAE,YAAY,GACd,yEACF;GACA,OAAO;EACT;EAEA,MAAM,MAAM,aAAa,aAAa,WAAW;EAEjD,MAAM,SAAwB,EAC5B,UAAU,CAAC,EACb;EACA,IAAI;GACF,MAAM,WAAW,MAAM,KAAK,KAAK,QAAQ,GAAG;GAU5C,MATmB,SAAS,MAAM,EAChC,mBAAmB;IACjB,QAAQ;IACR,UAAU;IACV,OAAO;GACT,EACF,CACiB,CAAC,CAAC,iBAAiB,GAEhC,CAAC,CACF,QAEE,SAAS,KAAK,cAAc,SAAS,KAAK,cAAc,IAC3D,CAAC,CACA,SAEE,SAAS;IASR,MAAM,cAAuB;KAC3B,SATsB,KAAK,UAAU,SAAS,GAAG,IAC/C,KAAK,UAAU,MAAM,GAAG,EAAE,IAC1B,KAAK;KAQP,kBANuB,YACvB,KAAK,aAAa,MAAM,UAAU,CAAC,EAAE,MAAM,MAAM,QAAQ,CAAC,CAAC,GAAG,EAK/C;IACjB;IAEA,OAAO,SAAS,KAAK,WAAW;GAClC,CACF;GAEF,IAAI,OAAO,SAAS,QAClB,OAAO,MACL;IAAE;IAAa;IAAa,UAAU,OAAO,SAAS;GAAO,GAC7D,6BACF;QAEA,OAAO,MACL;IAAE;IAAa;GAAY,GAC3B,gCACF;EAEJ,SAAS,KAAK;GACZ,IAAI,eAAeA,gBAAa,IAAI,UAAU,eAAe,KAAK;IAChE,OAAO,KACL;KAAE;KAAa;IAAY,GAC3B,gCACF;IACA,OAAO;GACT;GACA,KAAK,oBAAoB,GAAG;EAC9B;EAEA,OAAO,OAAO,SAAS,SAAS,SAAS;CAC3C;CAEA,YAAY,QAA0D;EACpE,OAAO,KAAK,OACV;GACE,KAAK,cAAc,OAAO,aAAa,OAAO,WAAW;GACzD,UAAU;EACZ,SACM,KAAK,cAAc,MAAM,CACjC;CACF;AACF"}
1
+ {"version":3,"file":"index.js","names":[],"sources":["../../../../lib/modules/datasource/artifactory/index.ts"],"sourcesContent":["import { logger } from '../../../logger/index.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { parse } from '../../../util/html.ts';\nimport { isNotFound } from '../../../util/http/status.ts';\nimport { regEx } from '../../../util/regex.ts';\nimport { asTimestamp } from '../../../util/timestamp.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { datasource } from './common.ts';\n\nexport class ArtifactoryDatasource extends Datasource {\n static readonly id = datasource;\n\n constructor() {\n super(datasource);\n }\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n\n override readonly registryStrategy = 'merge';\n\n override readonly releaseTimestampSupport = true;\n override readonly releaseTimestampNote =\n 'The release timestamp is determined from the date-like text, next to the version hyperlink tag in the results.';\n\n private async fetchReleases({\n packageName,\n registryUrl,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n if (!registryUrl) {\n logger.warn(\n { packageName },\n 'artifactory datasource requires custom registryUrl. Skipping datasource',\n );\n return null;\n }\n\n const url = joinUrlParts(registryUrl, packageName);\n\n const result: ReleaseResult = {\n releases: [],\n };\n try {\n const response = await this.http.getText(url);\n const body = parse(response.body, {\n blockTextElements: {\n script: true,\n noscript: true,\n style: true,\n },\n });\n const nodes = body.querySelectorAll('a');\n\n nodes\n .filter(\n // filter out hyperlink to navigate to parent folder\n (node) => node.innerHTML !== '../' && node.innerHTML !== '..',\n )\n .forEach(\n // extract version and published time for each node\n (node) => {\n const version: string = node.innerHTML.endsWith('/')\n ? node.innerHTML.slice(0, -1)\n : node.innerHTML;\n\n const releaseTimestamp = asTimestamp(\n node.nextSibling?.text?.trimStart()?.split(regEx(/\\s{2,}/))?.[0],\n );\n\n const thisRelease: Release = {\n version,\n releaseTimestamp,\n };\n\n result.releases.push(thisRelease);\n },\n );\n\n if (result.releases.length) {\n logger.trace(\n { registryUrl, packageName, versions: result.releases.length },\n 'artifactory: Found versions',\n );\n } else {\n logger.trace(\n { registryUrl, packageName },\n 'artifactory: No versions found',\n );\n }\n } catch (err) {\n if (isNotFound(err)) {\n logger.warn(\n { registryUrl, packageName },\n 'artifactory: `Not Found` error',\n );\n return null;\n }\n this.handleGenericErrors(err);\n }\n\n return result.releases.length ? result : null;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n return this.cached(\n {\n key: buildCacheKey(config.registryUrl, config.packageName),\n fallback: true,\n },\n () => this.fetchReleases(config),\n );\n }\n}\n"],"mappings":";;;;;;;;;;AAWA,IAAa,wBAAb,cAA2C,WAAW;CACpD,OAAgB,KAAK;CAErB,cAAc;EACZ,MAAM,UAAU;CAClB;CAEA,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CAEA,mBAAqC;CAErC,0BAA4C;CAC5C,uBACE;CAEF,MAAc,cAAc,EAC1B,aACA,eACmD;EACnD,IAAI,CAAC,aAAa;GAChB,OAAO,KACL,EAAE,YAAY,GACd,yEACF;GACA,OAAO;EACT;EAEA,MAAM,MAAM,aAAa,aAAa,WAAW;EAEjD,MAAM,SAAwB,EAC5B,UAAU,CAAC,EACb;EACA,IAAI;GACF,MAAM,WAAW,MAAM,KAAK,KAAK,QAAQ,GAAG;GAU5C,MATmB,SAAS,MAAM,EAChC,mBAAmB;IACjB,QAAQ;IACR,UAAU;IACV,OAAO;GACT,EACF,CACiB,CAAC,CAAC,iBAAiB,GAEhC,CAAC,CACF,QAEE,SAAS,KAAK,cAAc,SAAS,KAAK,cAAc,IAC3D,CAAC,CACA,SAEE,SAAS;IASR,MAAM,cAAuB;KAC3B,SATsB,KAAK,UAAU,SAAS,GAAG,IAC/C,KAAK,UAAU,MAAM,GAAG,EAAE,IAC1B,KAAK;KAQP,kBANuB,YACvB,KAAK,aAAa,MAAM,UAAU,CAAC,EAAE,MAAM,MAAM,QAAQ,CAAC,CAAC,GAAG,EAK/C;IACjB;IAEA,OAAO,SAAS,KAAK,WAAW;GAClC,CACF;GAEF,IAAI,OAAO,SAAS,QAClB,OAAO,MACL;IAAE;IAAa;IAAa,UAAU,OAAO,SAAS;GAAO,GAC7D,6BACF;QAEA,OAAO,MACL;IAAE;IAAa;GAAY,GAC3B,gCACF;EAEJ,SAAS,KAAK;GACZ,IAAI,WAAW,GAAG,GAAG;IACnB,OAAO,KACL;KAAE;KAAa;IAAY,GAC3B,gCACF;IACA,OAAO;GACT;GACA,KAAK,oBAAoB,GAAG;EAC9B;EAEA,OAAO,OAAO,SAAS,SAAS,SAAS;CAC3C;CAEA,YAAY,QAA0D;EACpE,OAAO,KAAK,OACV;GACE,KAAK,cAAc,OAAO,aAAa,OAAO,WAAW;GACzD,UAAU;EACZ,SACM,KAAK,cAAc,MAAM,CACjC;CACF;AACF"}
@@ -1,5 +1,6 @@
1
1
  import { buildCacheKey } from "../../../util/cache/package/key.js";
2
2
  import { joinUrlParts } from "../../../util/url.js";
3
+ import { isNotFound } from "../../../util/http/status.js";
3
4
  import { ExternalHostError } from "../../../types/errors/external-host-error.js";
4
5
  import { isValidLocalPath, readLocalFile } from "../../../util/fs/index.js";
5
6
  import { Json } from "../../../util/schema-utils/index.js";
@@ -49,7 +50,7 @@ var BazelDatasource = class BazelDatasource extends Datasource {
49
50
  if (metadata.homepage) result.homepage = metadata.homepage;
50
51
  } catch (err) {
51
52
  if (err instanceof RequestError) {
52
- if (err.response?.statusCode === 404) return null;
53
+ if (isNotFound(err)) return null;
53
54
  throw new ExternalHostError(err);
54
55
  }
55
56
  this.handleGenericErrors(err);
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["bazelVersioningId","HttpError"],"sources":["../../../../lib/modules/datasource/bazel/index.ts"],"sourcesContent":["import { isTruthy } from '@sindresorhus/is';\nimport { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { isValidLocalPath, readLocalFile } from '../../../util/fs/index.ts';\nimport { HttpError } from '../../../util/http/index.ts';\nimport { Json } from '../../../util/schema-utils/index.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { BzlmodVersion } from '../../versioning/bazel-module/bzlmod-version.ts';\nimport { id as bazelVersioningId } from '../../versioning/bazel-module/index.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { BazelModuleMetadata } from './schema.ts';\n\nexport class BazelDatasource extends Datasource {\n static readonly id = 'bazel';\n\n static readonly bazelCentralRepoUrl =\n 'https://raw.githubusercontent.com/bazelbuild/bazel-central-registry/main';\n\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return [BazelDatasource.bazelCentralRepoUrl];\n }\n override readonly registryStrategy = 'hunt';\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n override readonly defaultVersioning = bazelVersioningId;\n\n static packageMetadataPath(packageName: string): string {\n return `/modules/${packageName}/metadata.json`;\n }\n\n constructor() {\n super(BazelDatasource.id);\n }\n\n private async fetchReleases({\n registryUrl,\n packageName,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n const path = BazelDatasource.packageMetadataPath(packageName);\n const url = joinUrlParts(registryUrl!, path);\n const result: ReleaseResult = { releases: [] };\n try {\n let metadata: BazelModuleMetadata;\n const FILE_PREFIX = 'file://';\n if (url.startsWith(FILE_PREFIX)) {\n const filePath = url.slice(FILE_PREFIX.length);\n if (!isValidLocalPath(filePath)) {\n return null;\n }\n const fileContent = await readLocalFile(filePath, 'utf8');\n if (!fileContent) {\n return null;\n }\n metadata = Json.pipe(BazelModuleMetadata).parse(fileContent);\n } else {\n const response = await this.http.getJson(url, BazelModuleMetadata);\n metadata = response.body;\n }\n\n result.releases = metadata.versions\n .map((v) => new BzlmodVersion(v))\n .sort(BzlmodVersion.defaultCompare)\n .map((bv) => {\n const release: Release = { version: bv.original };\n if (isTruthy(metadata.yanked_versions?.[bv.original])) {\n release.isDeprecated = true;\n }\n return release;\n });\n if (metadata.homepage) {\n result.homepage = metadata.homepage;\n }\n } catch (err) {\n if (err instanceof HttpError) {\n if (err.response?.statusCode === 404) {\n return null;\n }\n throw new ExternalHostError(err);\n }\n this.handleGenericErrors(err);\n }\n\n return result.releases.length ? result : null;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n return this.cached(\n {\n key: buildCacheKey(config.registryUrl, config.packageName),\n fallback: true,\n },\n () => this.fetchReleases(config),\n );\n }\n}\n"],"mappings":";;;;;;;;;;;;;AAaA,IAAa,kBAAb,MAAa,wBAAwB,WAAW;CAC9C,OAAgB,KAAK;CAErB,OAAgB,sBACd;CAEF,uBAAgC,cAAgC;EAC9D,OAAO,CAAC,gBAAgB,mBAAmB;CAC7C;CACA,mBAAqC;CACrC,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CACA,oBAAsCA;CAEtC,OAAO,oBAAoB,aAA6B;EACtD,OAAO,YAAY,YAAY;CACjC;CAEA,cAAc;EACZ,MAAM,gBAAgB,EAAE;CAC1B;CAEA,MAAc,cAAc,EAC1B,aACA,eACmD;EACnD,MAAM,OAAO,gBAAgB,oBAAoB,WAAW;EAC5D,MAAM,MAAM,aAAa,aAAc,IAAI;EAC3C,MAAM,SAAwB,EAAE,UAAU,CAAC,EAAE;EAC7C,IAAI;GACF,IAAI;GAEJ,IAAI,IAAI,WAAW,SAAW,GAAG;IAC/B,MAAM,WAAW,IAAI,MAAM,CAAkB;IAC7C,IAAI,CAAC,iBAAiB,QAAQ,GAC5B,OAAO;IAET,MAAM,cAAc,MAAM,cAAc,UAAU,MAAM;IACxD,IAAI,CAAC,aACH,OAAO;IAET,WAAW,KAAK,KAAK,mBAAmB,CAAC,CAAC,MAAM,WAAW;GAC7D,OAEE,YAAW,MADY,KAAK,KAAK,QAAQ,KAAK,mBAAmB,EAAA,CAC7C;GAGtB,OAAO,WAAW,SAAS,SACxB,KAAK,MAAM,IAAI,cAAc,CAAC,CAAC,CAAC,CAChC,KAAK,cAAc,cAAc,CAAC,CAClC,KAAK,OAAO;IACX,MAAM,UAAmB,EAAE,SAAS,GAAG,SAAS;IAChD,IAAI,SAAS,SAAS,kBAAkB,GAAG,SAAS,GAClD,QAAQ,eAAe;IAEzB,OAAO;GACT,CAAC;GACH,IAAI,SAAS,UACX,OAAO,WAAW,SAAS;EAE/B,SAAS,KAAK;GACZ,IAAI,eAAeC,cAAW;IAC5B,IAAI,IAAI,UAAU,eAAe,KAC/B,OAAO;IAET,MAAM,IAAI,kBAAkB,GAAG;GACjC;GACA,KAAK,oBAAoB,GAAG;EAC9B;EAEA,OAAO,OAAO,SAAS,SAAS,SAAS;CAC3C;CAEA,YAAY,QAA0D;EACpE,OAAO,KAAK,OACV;GACE,KAAK,cAAc,OAAO,aAAa,OAAO,WAAW;GACzD,UAAU;EACZ,SACM,KAAK,cAAc,MAAM,CACjC;CACF;AACF"}
1
+ {"version":3,"file":"index.js","names":["bazelVersioningId","HttpError"],"sources":["../../../../lib/modules/datasource/bazel/index.ts"],"sourcesContent":["import { isTruthy } from '@sindresorhus/is';\nimport { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { isValidLocalPath, readLocalFile } from '../../../util/fs/index.ts';\nimport { HttpError } from '../../../util/http/index.ts';\nimport { isNotFound } from '../../../util/http/status.ts';\nimport { Json } from '../../../util/schema-utils/index.ts';\nimport { joinUrlParts } from '../../../util/url.ts';\nimport { BzlmodVersion } from '../../versioning/bazel-module/bzlmod-version.ts';\nimport { id as bazelVersioningId } from '../../versioning/bazel-module/index.ts';\nimport { Datasource } from '../datasource.ts';\nimport type { GetReleasesConfig, Release, ReleaseResult } from '../types.ts';\nimport { BazelModuleMetadata } from './schema.ts';\n\nexport class BazelDatasource extends Datasource {\n static readonly id = 'bazel';\n\n static readonly bazelCentralRepoUrl =\n 'https://raw.githubusercontent.com/bazelbuild/bazel-central-registry/main';\n\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return [BazelDatasource.bazelCentralRepoUrl];\n }\n override readonly registryStrategy = 'hunt';\n override supportsCustomRegistry(_packageName: string): boolean {\n return true;\n }\n override readonly defaultVersioning = bazelVersioningId;\n\n static packageMetadataPath(packageName: string): string {\n return `/modules/${packageName}/metadata.json`;\n }\n\n constructor() {\n super(BazelDatasource.id);\n }\n\n private async fetchReleases({\n registryUrl,\n packageName,\n }: GetReleasesConfig): Promise<ReleaseResult | null> {\n const path = BazelDatasource.packageMetadataPath(packageName);\n const url = joinUrlParts(registryUrl!, path);\n const result: ReleaseResult = { releases: [] };\n try {\n let metadata: BazelModuleMetadata;\n const FILE_PREFIX = 'file://';\n if (url.startsWith(FILE_PREFIX)) {\n const filePath = url.slice(FILE_PREFIX.length);\n if (!isValidLocalPath(filePath)) {\n return null;\n }\n const fileContent = await readLocalFile(filePath, 'utf8');\n if (!fileContent) {\n return null;\n }\n metadata = Json.pipe(BazelModuleMetadata).parse(fileContent);\n } else {\n const response = await this.http.getJson(url, BazelModuleMetadata);\n metadata = response.body;\n }\n\n result.releases = metadata.versions\n .map((v) => new BzlmodVersion(v))\n .sort(BzlmodVersion.defaultCompare)\n .map((bv) => {\n const release: Release = { version: bv.original };\n if (isTruthy(metadata.yanked_versions?.[bv.original])) {\n release.isDeprecated = true;\n }\n return release;\n });\n if (metadata.homepage) {\n result.homepage = metadata.homepage;\n }\n } catch (err) {\n if (err instanceof HttpError) {\n if (isNotFound(err)) {\n return null;\n }\n throw new ExternalHostError(err);\n }\n this.handleGenericErrors(err);\n }\n\n return result.releases.length ? result : null;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n return this.cached(\n {\n key: buildCacheKey(config.registryUrl, config.packageName),\n fallback: true,\n },\n () => this.fetchReleases(config),\n );\n }\n}\n"],"mappings":";;;;;;;;;;;;;;AAcA,IAAa,kBAAb,MAAa,wBAAwB,WAAW;CAC9C,OAAgB,KAAK;CAErB,OAAgB,sBACd;CAEF,uBAAgC,cAAgC;EAC9D,OAAO,CAAC,gBAAgB,mBAAmB;CAC7C;CACA,mBAAqC;CACrC,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CACA,oBAAsCA;CAEtC,OAAO,oBAAoB,aAA6B;EACtD,OAAO,YAAY,YAAY;CACjC;CAEA,cAAc;EACZ,MAAM,gBAAgB,EAAE;CAC1B;CAEA,MAAc,cAAc,EAC1B,aACA,eACmD;EACnD,MAAM,OAAO,gBAAgB,oBAAoB,WAAW;EAC5D,MAAM,MAAM,aAAa,aAAc,IAAI;EAC3C,MAAM,SAAwB,EAAE,UAAU,CAAC,EAAE;EAC7C,IAAI;GACF,IAAI;GAEJ,IAAI,IAAI,WAAW,SAAW,GAAG;IAC/B,MAAM,WAAW,IAAI,MAAM,CAAkB;IAC7C,IAAI,CAAC,iBAAiB,QAAQ,GAC5B,OAAO;IAET,MAAM,cAAc,MAAM,cAAc,UAAU,MAAM;IACxD,IAAI,CAAC,aACH,OAAO;IAET,WAAW,KAAK,KAAK,mBAAmB,CAAC,CAAC,MAAM,WAAW;GAC7D,OAEE,YAAW,MADY,KAAK,KAAK,QAAQ,KAAK,mBAAmB,EAAA,CAC7C;GAGtB,OAAO,WAAW,SAAS,SACxB,KAAK,MAAM,IAAI,cAAc,CAAC,CAAC,CAAC,CAChC,KAAK,cAAc,cAAc,CAAC,CAClC,KAAK,OAAO;IACX,MAAM,UAAmB,EAAE,SAAS,GAAG,SAAS;IAChD,IAAI,SAAS,SAAS,kBAAkB,GAAG,SAAS,GAClD,QAAQ,eAAe;IAEzB,OAAO;GACT,CAAC;GACH,IAAI,SAAS,UACX,OAAO,WAAW,SAAS;EAE/B,SAAS,KAAK;GACZ,IAAI,eAAeC,cAAW;IAC5B,IAAI,WAAW,GAAG,GAChB,OAAO;IAET,MAAM,IAAI,kBAAkB,GAAG;GACjC;GACA,KAAK,oBAAoB,GAAG;EAC9B;EAEA,OAAO,OAAO,SAAS,SAAS,SAAS;CAC3C;CAEA,YAAY,QAA0D;EACpE,OAAO,KAAK,OACV;GACE,KAAK,cAAc,OAAO,aAAa,OAAO,WAAW;GACzD,UAAU;EACZ,SACM,KAAK,cAAc,MAAM,CACjC;CACF;AACF"}
@@ -1,4 +1,5 @@
1
1
  import { buildCacheKey } from "../../../util/cache/package/key.js";
2
+ import { isNotFound } from "../../../util/http/status.js";
2
3
  import { ExternalHostError } from "../../../types/errors/external-host-error.js";
3
4
  import { withCache } from "../../../util/cache/package/with-cache.js";
4
5
  import { Datasource } from "../datasource.js";
@@ -59,7 +60,7 @@ var CdnjsDatasource = class CdnjsDatasource extends Datasource {
59
60
  }, () => this._getDigest(config, newValue));
60
61
  }
61
62
  handleHttpErrors(err) {
62
- if (err.response?.statusCode !== 404) throw new ExternalHostError(err);
63
+ if (!isNotFound(err)) throw new ExternalHostError(err);
63
64
  }
64
65
  };
65
66
  export { CdnjsDatasource };
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":[],"sources":["../../../../lib/modules/datasource/cdnjs/index.ts"],"sourcesContent":["import { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { withCache } from '../../../util/cache/package/with-cache.ts';\nimport { memCacheProvider } from '../../../util/http/cache/memory-http-cache-provider.ts';\nimport type { HttpError } from '../../../util/http/index.ts';\nimport { Datasource } from '../datasource.ts';\nimport type {\n DigestConfig,\n GetReleasesConfig,\n Release,\n ReleaseResult,\n} from '../types.ts';\nimport { CdnjsAPISriResponse, CdnjsAPIVersionResponse } from './schema.ts';\n\nexport class CdnjsDatasource extends Datasource {\n static readonly id = 'cdnjs';\n\n constructor() {\n super(CdnjsDatasource.id);\n }\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return false;\n }\n\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return ['https://api.cdnjs.com/'];\n }\n\n override readonly sourceUrlSupport = 'package';\n override readonly sourceUrlNote =\n 'The source URL is determined from the `repository` field in the results.';\n\n private async _getReleases(\n config: GetReleasesConfig,\n ): Promise<ReleaseResult | null> {\n const { packageName, registryUrl } = config;\n /* v8 ignore next -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n const [library] = packageName.split('/');\n\n const url = `${registryUrl}libraries/${library}?fields=homepage,repository,versions`;\n\n const body = await this.fetchJsonOrNull(url, CdnjsAPIVersionResponse, {\n cacheProvider: memCacheProvider,\n });\n if (!body) {\n return null;\n }\n\n const { versions, homepage, repository } = body;\n const releases: Release[] = versions;\n\n const res: ReleaseResult = { releases };\n\n if (homepage) {\n res.homepage = homepage;\n }\n\n if (repository) {\n res.sourceUrl = repository;\n }\n\n return res;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n const library = config.packageName.split('/')[0];\n return withCache(\n {\n namespace: `datasource-${CdnjsDatasource.id}`,\n key: buildCacheKey('getReleases', library),\n public: true,\n fallback: true,\n },\n () => this._getReleases(config),\n );\n }\n\n private async _getDigest(\n config: DigestConfig,\n newValue: string,\n ): Promise<string | null> {\n const { packageName, registryUrl } = config;\n /* v8 ignore next -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n const [library] = packageName.split('/');\n const assetName = packageName.replace(`${library}/`, '');\n\n const url = `${registryUrl}libraries/${library}/${newValue}?fields=sri`;\n\n const body = await this.fetchJsonOrNull(url, CdnjsAPISriResponse);\n\n return body?.sri?.[assetName] ?? null;\n }\n\n override getDigest(\n config: DigestConfig,\n newValue: string,\n ): Promise<string | null> {\n return withCache(\n {\n namespace: `datasource-${CdnjsDatasource.id}`,\n key: buildCacheKey(\n 'getDigest',\n config.registryUrl,\n config.packageName,\n newValue,\n ),\n public: true,\n fallback: true,\n },\n () => this._getDigest(config, newValue),\n );\n }\n\n override handleHttpErrors(err: HttpError): void {\n if (err.response?.statusCode !== 404) {\n throw new ExternalHostError(err);\n }\n }\n}\n"],"mappings":";;;;;;;AAcA,IAAa,kBAAb,MAAa,wBAAwB,WAAW;CAC9C,OAAgB,KAAK;CAErB,cAAc;EACZ,MAAM,gBAAgB,EAAE;CAC1B;CAEA,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CAEA,uBAAgC,cAAgC;EAC9D,OAAO,CAAC,wBAAwB;CAClC;CAEA,mBAAqC;CACrC,gBACE;CAEF,MAAc,aACZ,QAC+B;EAC/B,MAAM,EAAE,aAAa,gBAAgB;;EAErC,IAAI,CAAC,aACH,OAAO;EAGT,MAAM,CAAC,WAAW,YAAY,MAAM,GAAG;EAEvC,MAAM,MAAM,GAAG,YAAY,YAAY,QAAQ;EAE/C,MAAM,OAAO,MAAM,KAAK,gBAAgB,KAAK,yBAAyB,EACpE,eAAe,iBACjB,CAAC;EACD,IAAI,CAAC,MACH,OAAO;EAGT,MAAM,EAAE,UAAU,UAAU,eAAe;EAG3C,MAAM,MAAqB,EAAE,UAAA,SAAS;EAEtC,IAAI,UACF,IAAI,WAAW;EAGjB,IAAI,YACF,IAAI,YAAY;EAGlB,OAAO;CACT;CAEA,YAAY,QAA0D;EACpE,MAAM,UAAU,OAAO,YAAY,MAAM,GAAG,CAAC,CAAC;EAC9C,OAAO,UACL;GACE,WAAW,cAAc,gBAAgB;GACzC,KAAK,cAAc,eAAe,OAAO;GACzC,QAAQ;GACR,UAAU;EACZ,SACM,KAAK,aAAa,MAAM,CAChC;CACF;CAEA,MAAc,WACZ,QACA,UACwB;EACxB,MAAM,EAAE,aAAa,gBAAgB;;EAErC,IAAI,CAAC,aACH,OAAO;EAGT,MAAM,CAAC,WAAW,YAAY,MAAM,GAAG;EACvC,MAAM,YAAY,YAAY,QAAQ,GAAG,QAAQ,IAAI,EAAE;EAEvD,MAAM,MAAM,GAAG,YAAY,YAAY,QAAQ,GAAG,SAAS;EAI3D,QAAO,MAFY,KAAK,gBAAgB,KAAK,mBAAmB,EAAA,EAEnD,MAAM,cAAc;CACnC;CAEA,UACE,QACA,UACwB;EACxB,OAAO,UACL;GACE,WAAW,cAAc,gBAAgB;GACzC,KAAK,cACH,aACA,OAAO,aACP,OAAO,aACP,QACF;GACA,QAAQ;GACR,UAAU;EACZ,SACM,KAAK,WAAW,QAAQ,QAAQ,CACxC;CACF;CAEA,iBAA0B,KAAsB;EAC9C,IAAI,IAAI,UAAU,eAAe,KAC/B,MAAM,IAAI,kBAAkB,GAAG;CAEnC;AACF"}
1
+ {"version":3,"file":"index.js","names":[],"sources":["../../../../lib/modules/datasource/cdnjs/index.ts"],"sourcesContent":["import { ExternalHostError } from '../../../types/errors/external-host-error.ts';\nimport { buildCacheKey } from '../../../util/cache/package/key.ts';\nimport { withCache } from '../../../util/cache/package/with-cache.ts';\nimport { memCacheProvider } from '../../../util/http/cache/memory-http-cache-provider.ts';\nimport type { HttpError } from '../../../util/http/index.ts';\nimport { isNotFound } from '../../../util/http/status.ts';\nimport { Datasource } from '../datasource.ts';\nimport type {\n DigestConfig,\n GetReleasesConfig,\n Release,\n ReleaseResult,\n} from '../types.ts';\nimport { CdnjsAPISriResponse, CdnjsAPIVersionResponse } from './schema.ts';\n\nexport class CdnjsDatasource extends Datasource {\n static readonly id = 'cdnjs';\n\n constructor() {\n super(CdnjsDatasource.id);\n }\n\n override supportsCustomRegistry(_packageName: string): boolean {\n return false;\n }\n\n override getDefaultRegistryUrls(_packageName: string): string[] {\n return ['https://api.cdnjs.com/'];\n }\n\n override readonly sourceUrlSupport = 'package';\n override readonly sourceUrlNote =\n 'The source URL is determined from the `repository` field in the results.';\n\n private async _getReleases(\n config: GetReleasesConfig,\n ): Promise<ReleaseResult | null> {\n const { packageName, registryUrl } = config;\n /* v8 ignore next -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n const [library] = packageName.split('/');\n\n const url = `${registryUrl}libraries/${library}?fields=homepage,repository,versions`;\n\n const body = await this.fetchJsonOrNull(url, CdnjsAPIVersionResponse, {\n cacheProvider: memCacheProvider,\n });\n if (!body) {\n return null;\n }\n\n const { versions, homepage, repository } = body;\n const releases: Release[] = versions;\n\n const res: ReleaseResult = { releases };\n\n if (homepage) {\n res.homepage = homepage;\n }\n\n if (repository) {\n res.sourceUrl = repository;\n }\n\n return res;\n }\n\n getReleases(config: GetReleasesConfig): Promise<ReleaseResult | null> {\n const library = config.packageName.split('/')[0];\n return withCache(\n {\n namespace: `datasource-${CdnjsDatasource.id}`,\n key: buildCacheKey('getReleases', library),\n public: true,\n fallback: true,\n },\n () => this._getReleases(config),\n );\n }\n\n private async _getDigest(\n config: DigestConfig,\n newValue: string,\n ): Promise<string | null> {\n const { packageName, registryUrl } = config;\n /* v8 ignore next -- should never happen */\n if (!registryUrl) {\n return null;\n }\n\n const [library] = packageName.split('/');\n const assetName = packageName.replace(`${library}/`, '');\n\n const url = `${registryUrl}libraries/${library}/${newValue}?fields=sri`;\n\n const body = await this.fetchJsonOrNull(url, CdnjsAPISriResponse);\n\n return body?.sri?.[assetName] ?? null;\n }\n\n override getDigest(\n config: DigestConfig,\n newValue: string,\n ): Promise<string | null> {\n return withCache(\n {\n namespace: `datasource-${CdnjsDatasource.id}`,\n key: buildCacheKey(\n 'getDigest',\n config.registryUrl,\n config.packageName,\n newValue,\n ),\n public: true,\n fallback: true,\n },\n () => this._getDigest(config, newValue),\n );\n }\n\n override handleHttpErrors(err: HttpError): void {\n if (!isNotFound(err)) {\n throw new ExternalHostError(err);\n }\n }\n}\n"],"mappings":";;;;;;;;AAeA,IAAa,kBAAb,MAAa,wBAAwB,WAAW;CAC9C,OAAgB,KAAK;CAErB,cAAc;EACZ,MAAM,gBAAgB,EAAE;CAC1B;CAEA,uBAAgC,cAA+B;EAC7D,OAAO;CACT;CAEA,uBAAgC,cAAgC;EAC9D,OAAO,CAAC,wBAAwB;CAClC;CAEA,mBAAqC;CACrC,gBACE;CAEF,MAAc,aACZ,QAC+B;EAC/B,MAAM,EAAE,aAAa,gBAAgB;;EAErC,IAAI,CAAC,aACH,OAAO;EAGT,MAAM,CAAC,WAAW,YAAY,MAAM,GAAG;EAEvC,MAAM,MAAM,GAAG,YAAY,YAAY,QAAQ;EAE/C,MAAM,OAAO,MAAM,KAAK,gBAAgB,KAAK,yBAAyB,EACpE,eAAe,iBACjB,CAAC;EACD,IAAI,CAAC,MACH,OAAO;EAGT,MAAM,EAAE,UAAU,UAAU,eAAe;EAG3C,MAAM,MAAqB,EAAE,UAAA,SAAS;EAEtC,IAAI,UACF,IAAI,WAAW;EAGjB,IAAI,YACF,IAAI,YAAY;EAGlB,OAAO;CACT;CAEA,YAAY,QAA0D;EACpE,MAAM,UAAU,OAAO,YAAY,MAAM,GAAG,CAAC,CAAC;EAC9C,OAAO,UACL;GACE,WAAW,cAAc,gBAAgB;GACzC,KAAK,cAAc,eAAe,OAAO;GACzC,QAAQ;GACR,UAAU;EACZ,SACM,KAAK,aAAa,MAAM,CAChC;CACF;CAEA,MAAc,WACZ,QACA,UACwB;EACxB,MAAM,EAAE,aAAa,gBAAgB;;EAErC,IAAI,CAAC,aACH,OAAO;EAGT,MAAM,CAAC,WAAW,YAAY,MAAM,GAAG;EACvC,MAAM,YAAY,YAAY,QAAQ,GAAG,QAAQ,IAAI,EAAE;EAEvD,MAAM,MAAM,GAAG,YAAY,YAAY,QAAQ,GAAG,SAAS;EAI3D,QAAO,MAFY,KAAK,gBAAgB,KAAK,mBAAmB,EAAA,EAEnD,MAAM,cAAc;CACnC;CAEA,UACE,QACA,UACwB;EACxB,OAAO,UACL;GACE,WAAW,cAAc,gBAAgB;GACzC,KAAK,cACH,aACA,OAAO,aACP,OAAO,aACP,QACF;GACA,QAAQ;GACR,UAAU;EACZ,SACM,KAAK,WAAW,QAAQ,QAAQ,CACxC;CACF;CAEA,iBAA0B,KAAsB;EAC9C,IAAI,CAAC,WAAW,GAAG,GACjB,MAAM,IAAI,kBAAkB,GAAG;CAEnC;AACF"}
@@ -7,6 +7,15 @@ export declare function getDatasourceHostType(datasource: string): string | null
7
7
  export declare function getDefaultVersioning(datasourceName: string | undefined): string;
8
8
  export declare function isGetPkgReleasesConfig(input: unknown): input is GetPkgReleasesConfig;
9
9
  export declare function applyVersionCompatibility(releaseResult: ReleaseResult, versionCompatibility: string | undefined, currentCompatibility: string | undefined): ReleaseResult;
10
+ /**
11
+ * Extracts a version string from regex named capture groups.
12
+ *
13
+ * Supports two modes:
14
+ * 1. A `version` group: returned as-is.
15
+ * 2. SemVer-part groups (`major`, `minor`, `patch`, `prerelease`, `build`):
16
+ * assembled into `MAJOR.MINOR.PATCH[-PRERELEASE][+BUILD]`.
17
+ */
18
+ export declare function extractVersionFromGroups(groups: Record<string, string> | undefined): string | undefined;
10
19
  export declare function applyExtractVersion(releaseResult: ReleaseResult, extractVersion: string | undefined): ReleaseResult;
11
20
  export declare function filterValidVersions<Config extends Pick<GetPkgReleasesConfig, 'versioning' | 'datasource'>>(releaseResult: ReleaseResult, config: Config): ReleaseResult;
12
21
  export declare function sortAndRemoveDuplicates<Config extends Pick<GetPkgReleasesConfig, 'versioning' | 'datasource'>>(releaseResult: ReleaseResult, config: Config): ReleaseResult;