dependabot-maven 0.308.0 → 0.309.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.
- checksums.yaml +4 -4
- data/lib/dependabot/maven/file_parser/property_value_finder.rb +7 -1
- data/lib/dependabot/maven/file_parser/repositories_finder.rb +64 -10
- data/lib/dependabot/maven/file_parser.rb +1 -1
- data/lib/dependabot/maven/file_updater/declaration_finder.rb +43 -11
- data/lib/dependabot/maven/file_updater/property_value_updater.rb +1 -2
- data/lib/dependabot/maven/file_updater.rb +80 -18
- data/lib/dependabot/maven/metadata_finder.rb +2 -0
- data/lib/dependabot/maven/package/package_details_fetcher.rb +485 -0
- data/lib/dependabot/maven/requirement.rb +32 -15
- data/lib/dependabot/maven/update_checker/property_updater.rb +79 -24
- data/lib/dependabot/maven/update_checker/version_finder.rb +103 -272
- data/lib/dependabot/maven/update_checker.rb +4 -2
- metadata +6 -5
@@ -1,51 +1,75 @@
|
|
1
|
-
# typed:
|
1
|
+
# typed: strict
|
2
2
|
# frozen_string_literal: true
|
3
3
|
|
4
|
+
require "dependabot/package/release_cooldown_options"
|
4
5
|
require "dependabot/maven/file_parser"
|
5
6
|
require "dependabot/maven/update_checker"
|
6
7
|
require "dependabot/maven/file_updater/declaration_finder"
|
8
|
+
require "sorbet-runtime"
|
7
9
|
|
8
10
|
module Dependabot
|
9
11
|
module Maven
|
10
12
|
class UpdateChecker
|
11
13
|
class PropertyUpdater
|
14
|
+
extend T::Sig
|
12
15
|
require_relative "requirements_updater"
|
13
16
|
require_relative "version_finder"
|
14
17
|
|
15
|
-
|
16
|
-
|
18
|
+
sig do
|
19
|
+
params(
|
20
|
+
dependency: Dependabot::Dependency,
|
21
|
+
dependency_files: T::Array[Dependabot::DependencyFile],
|
22
|
+
credentials: T::Array[Dependabot::Credential],
|
23
|
+
ignored_versions: T::Array[String],
|
24
|
+
target_version_details: T.nilable(T::Hash[T.untyped, T.untyped]),
|
25
|
+
update_cooldown: T.nilable(Dependabot::Package::ReleaseCooldownOptions)
|
26
|
+
).void
|
27
|
+
end
|
28
|
+
def initialize(
|
29
|
+
dependency:, dependency_files:, credentials:,
|
30
|
+
ignored_versions:, target_version_details:,
|
31
|
+
update_cooldown: nil
|
32
|
+
)
|
17
33
|
@dependency = dependency
|
18
34
|
@dependency_files = dependency_files
|
19
35
|
@credentials = credentials
|
20
36
|
@ignored_versions = ignored_versions
|
21
|
-
@target_version = target_version_details&.fetch(:version)
|
22
|
-
@source_url = target_version_details&.fetch(:source_url)
|
37
|
+
@target_version = T.let(target_version_details&.fetch(:version), T.nilable(Dependabot::Maven::Version))
|
38
|
+
@source_url = T.let(target_version_details&.fetch(:source_url), T.nilable(String))
|
39
|
+
@update_cooldown = update_cooldown
|
23
40
|
end
|
24
41
|
|
42
|
+
sig { returns(T::Boolean) }
|
25
43
|
def update_possible?
|
26
44
|
return false unless target_version
|
27
|
-
return @update_possible if defined?(@update_possible)
|
45
|
+
return T.must(@update_possible) if defined?(@update_possible)
|
28
46
|
|
29
|
-
@update_possible
|
47
|
+
@update_possible ||= T.let(
|
30
48
|
dependencies_using_property.all? do |dep|
|
31
49
|
next false if includes_property_reference?(updated_version(dep))
|
32
50
|
|
33
|
-
|
51
|
+
releases = VersionFinder.new(
|
34
52
|
dependency: dep,
|
35
53
|
dependency_files: dependency_files,
|
36
54
|
credentials: credentials,
|
37
55
|
ignored_versions: ignored_versions,
|
38
|
-
security_advisories: []
|
39
|
-
|
56
|
+
security_advisories: [],
|
57
|
+
cooldown_options: update_cooldown
|
58
|
+
).releases
|
59
|
+
|
60
|
+
versions = releases.map(&:version)
|
40
61
|
|
41
62
|
versions.include?(updated_version(dep)) || versions.none?
|
42
|
-
end
|
63
|
+
end,
|
64
|
+
T.nilable(T::Boolean)
|
65
|
+
)
|
43
66
|
end
|
44
67
|
|
68
|
+
sig { returns(T::Array[Dependabot::Dependency]) }
|
45
69
|
def updated_dependencies
|
46
70
|
raise "Update not possible!" unless update_possible?
|
47
71
|
|
48
|
-
@updated_dependencies ||=
|
72
|
+
@updated_dependencies ||= T.let(
|
49
73
|
dependencies_using_property.map do |dep|
|
50
74
|
Dependency.new(
|
51
75
|
name: dep.name,
|
@@ -55,20 +79,37 @@ module Dependabot
|
|
55
79
|
previous_requirements: dep.requirements,
|
56
80
|
package_manager: dep.package_manager
|
57
81
|
)
|
58
|
-
end
|
82
|
+
end,
|
83
|
+
T.nilable(T::Array[Dependabot::Dependency])
|
84
|
+
)
|
59
85
|
end
|
60
86
|
|
61
87
|
private
|
62
88
|
|
89
|
+
sig { returns(Dependabot::Dependency) }
|
63
90
|
attr_reader :dependency
|
91
|
+
|
92
|
+
sig { returns(T::Array[Dependabot::DependencyFile]) }
|
64
93
|
attr_reader :dependency_files
|
94
|
+
|
95
|
+
sig { returns(T.nilable(Dependabot::Maven::Version)) }
|
65
96
|
attr_reader :target_version
|
97
|
+
|
98
|
+
sig { returns(T.nilable(String)) }
|
66
99
|
attr_reader :source_url
|
100
|
+
|
101
|
+
sig { returns(T::Array[Dependabot::Credential]) }
|
67
102
|
attr_reader :credentials
|
103
|
+
|
104
|
+
sig { returns(T::Array[String]) }
|
68
105
|
attr_reader :ignored_versions
|
69
106
|
|
107
|
+
sig { returns(T.nilable(Dependabot::Package::ReleaseCooldownOptions)) }
|
108
|
+
attr_reader :update_cooldown
|
109
|
+
|
110
|
+
sig { returns(T::Array[Dependabot::Dependency]) }
|
70
111
|
def dependencies_using_property
|
71
|
-
@dependencies_using_property ||=
|
112
|
+
@dependencies_using_property ||= T.let(
|
72
113
|
Maven::FileParser.new(
|
73
114
|
dependency_files: dependency_files,
|
74
115
|
source: nil
|
@@ -78,30 +119,41 @@ module Dependabot
|
|
78
119
|
|
79
120
|
r.dig(:metadata, :property_source) == property_source
|
80
121
|
end
|
81
|
-
end
|
122
|
+
end,
|
123
|
+
T.nilable(T::Array[Dependabot::Dependency])
|
124
|
+
)
|
82
125
|
end
|
83
126
|
|
127
|
+
sig { returns(String) }
|
84
128
|
def property_name
|
85
|
-
@property_name ||=
|
86
|
-
|
87
|
-
|
129
|
+
@property_name ||= T.let(
|
130
|
+
dependency.requirements
|
131
|
+
.find { |r| r.dig(:metadata, :property_name) }
|
132
|
+
&.dig(:metadata, :property_name),
|
133
|
+
T.nilable(String)
|
134
|
+
)
|
88
135
|
|
89
136
|
raise "No requirement with a property name!" unless @property_name
|
90
137
|
|
91
138
|
@property_name
|
92
139
|
end
|
93
140
|
|
141
|
+
sig { returns(T.nilable(String)) }
|
94
142
|
def property_source
|
95
|
-
@property_source ||=
|
143
|
+
@property_source ||= T.let(
|
96
144
|
dependency.requirements
|
97
145
|
.find { |r| r.dig(:metadata, :property_name) == property_name }
|
98
|
-
&.dig(:metadata, :property_source)
|
146
|
+
&.dig(:metadata, :property_source),
|
147
|
+
T.nilable(String)
|
148
|
+
)
|
99
149
|
end
|
100
150
|
|
151
|
+
sig { params(string: String).returns(T::Boolean) }
|
101
152
|
def includes_property_reference?(string)
|
102
153
|
string.match?(Maven::FileParser::PROPERTY_REGEX)
|
103
154
|
end
|
104
155
|
|
156
|
+
sig { params(dep: Dependabot::Dependency).returns(T.nilable(String)) }
|
105
157
|
def version_string(dep)
|
106
158
|
declaring_requirement =
|
107
159
|
dep.requirements
|
@@ -109,21 +161,24 @@ module Dependabot
|
|
109
161
|
|
110
162
|
Maven::FileUpdater::DeclarationFinder.new(
|
111
163
|
dependency: dep,
|
112
|
-
declaring_requirement: declaring_requirement,
|
164
|
+
declaring_requirement: T.must(declaring_requirement),
|
113
165
|
dependency_files: dependency_files
|
114
|
-
).declaration_nodes.first
|
166
|
+
).declaration_nodes.first&.at_css("version")&.content
|
115
167
|
end
|
116
168
|
|
169
|
+
sig { returns(T.nilable(Dependabot::DependencyFile)) }
|
117
170
|
def pom
|
118
171
|
dependency_files.find { |f| f.name == "pom.xml" }
|
119
172
|
end
|
120
173
|
|
174
|
+
sig { params(dep: Dependabot::Dependency).returns(String) }
|
121
175
|
def updated_version(dep)
|
122
|
-
version_string(dep).gsub("${#{property_name}}", target_version.to_s)
|
176
|
+
T.must(version_string(dep)).gsub("${#{property_name}}", T.must(target_version).to_s)
|
123
177
|
end
|
124
178
|
|
179
|
+
sig { params(dep: Dependabot::Dependency).returns(T::Array[T::Hash[Symbol, T.untyped]]) }
|
125
180
|
def updated_requirements(dep)
|
126
|
-
@updated_requirements ||= {}
|
181
|
+
@updated_requirements ||= T.let({}, T.nilable(T::Hash[String, T::Array[T::Hash[Symbol, T.untyped]]]))
|
127
182
|
@updated_requirements[dep.name] ||=
|
128
183
|
RequirementsUpdater.new(
|
129
184
|
requirements: dep.requirements,
|
@@ -1,20 +1,17 @@
|
|
1
|
-
# typed:
|
1
|
+
# typed: strong
|
2
2
|
# frozen_string_literal: true
|
3
3
|
|
4
|
-
require "
|
4
|
+
require "dependabot/package/package_latest_version_finder"
|
5
|
+
require "dependabot/package/release_cooldown_options"
|
5
6
|
require "dependabot/update_checkers/version_filters"
|
6
|
-
require "dependabot/maven/
|
7
|
+
require "dependabot/maven/package/package_details_fetcher"
|
7
8
|
require "dependabot/maven/update_checker"
|
8
|
-
require "dependabot/maven/version"
|
9
|
-
require "dependabot/maven/requirement"
|
10
|
-
require "dependabot/maven/utils/auth_headers_finder"
|
11
|
-
require "dependabot/registry_client"
|
12
9
|
require "sorbet-runtime"
|
13
10
|
|
14
11
|
module Dependabot
|
15
12
|
module Maven
|
16
13
|
class UpdateChecker
|
17
|
-
class VersionFinder
|
14
|
+
class VersionFinder < Dependabot::Package::PackageLatestVersionFinder
|
18
15
|
extend T::Sig
|
19
16
|
|
20
17
|
TYPE_SUFFICES = %w(jre android java native_mt agp).freeze
|
@@ -26,18 +23,13 @@ module Dependabot
|
|
26
23
|
credentials: T::Array[Dependabot::Credential],
|
27
24
|
ignored_versions: T::Array[String],
|
28
25
|
security_advisories: T::Array[Dependabot::SecurityAdvisory],
|
26
|
+
cooldown_options: T.nilable(Dependabot::Package::ReleaseCooldownOptions),
|
29
27
|
raise_on_ignored: T::Boolean
|
30
28
|
).void
|
31
29
|
end
|
32
30
|
def initialize(dependency:, dependency_files:, credentials:,
|
33
31
|
ignored_versions:, security_advisories:,
|
34
|
-
raise_on_ignored: false)
|
35
|
-
@dependency = dependency
|
36
|
-
@dependency_files = dependency_files
|
37
|
-
@credentials = credentials
|
38
|
-
@ignored_versions = ignored_versions
|
39
|
-
@raise_on_ignored = raise_on_ignored
|
40
|
-
@security_advisories = security_advisories
|
32
|
+
cooldown_options: nil, raise_on_ignored: false)
|
41
33
|
@forbidden_urls = T.let([], T::Array[String])
|
42
34
|
@dependency_metadata = T.let({}, T::Hash[T.untyped, Nokogiri::XML::Document])
|
43
35
|
@auth_headers_finder = T.let(nil, T.nilable(Utils::AuthHeadersFinder))
|
@@ -45,94 +37,133 @@ module Dependabot
|
|
45
37
|
@repository_finder = T.let(nil, T.nilable(Maven::FileParser::RepositoriesFinder))
|
46
38
|
@repositories = T.let(nil, T.nilable(T::Array[T::Hash[String, T.untyped]]))
|
47
39
|
@released_check = T.let({}, T::Hash[Version, T::Boolean])
|
40
|
+
@package_details_fetcher = T.let(nil, T.nilable(Package::PackageDetailsFetcher))
|
41
|
+
@package_details = T.let(nil, T.nilable(Dependabot::Package::PackageDetails))
|
42
|
+
super
|
48
43
|
end
|
49
44
|
|
50
|
-
sig { returns(T.nilable(
|
51
|
-
def
|
52
|
-
|
45
|
+
sig { override.returns(T.nilable(Dependabot::Package::PackageDetails)) }
|
46
|
+
def package_details
|
47
|
+
@package_details ||= package_details_fetcher.fetch
|
48
|
+
end
|
53
49
|
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
50
|
+
sig { returns(T::Array[Dependabot::Package::PackageRelease]) }
|
51
|
+
def releases
|
52
|
+
(package_details&.releases || []).reverse
|
53
|
+
end
|
58
54
|
|
59
|
-
|
55
|
+
sig { returns(T.nilable(T::Hash[T.untyped, T.untyped])) }
|
56
|
+
def latest_version_details
|
57
|
+
release = fetch_latest_release
|
58
|
+
release ? { version: release.version, source_url: release.url } : nil
|
60
59
|
end
|
61
60
|
|
62
61
|
sig { returns(T.nilable(T::Hash[T.untyped, T.untyped])) }
|
63
62
|
def lowest_security_fix_version_details
|
64
|
-
|
63
|
+
release = fetch_lowest_security_fix_release
|
64
|
+
release ? { version: release.version, source_url: release.url } : nil
|
65
|
+
end
|
65
66
|
|
66
|
-
|
67
|
-
possible_versions = filter_date_based_versions(possible_versions)
|
68
|
-
possible_versions = filter_version_types(possible_versions)
|
69
|
-
possible_versions = Dependabot::UpdateCheckers::VersionFilters.filter_vulnerable_versions(possible_versions,
|
70
|
-
security_advisories)
|
71
|
-
possible_versions = filter_ignored_versions(possible_versions)
|
72
|
-
possible_versions = filter_lower_versions(possible_versions)
|
67
|
+
protected
|
73
68
|
|
74
|
-
|
69
|
+
sig { returns(T::Boolean) }
|
70
|
+
def cooldown_enabled?
|
71
|
+
Dependabot::Experiments.enabled?(:enable_cooldown_for_maven)
|
75
72
|
end
|
76
73
|
|
77
|
-
sig
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
74
|
+
sig do
|
75
|
+
params(language_version: T.nilable(T.any(String, Dependabot::Version)))
|
76
|
+
.returns(T.nilable(Dependabot::Version))
|
77
|
+
end
|
78
|
+
def fetch_latest_version(language_version: nil)
|
79
|
+
fetch_latest_release(language_version: language_version)&.version
|
80
|
+
end
|
84
81
|
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
82
|
+
sig do
|
83
|
+
params(language_version: T.nilable(T.any(String, Dependabot::Version)))
|
84
|
+
.returns(T.nilable(Dependabot::Version))
|
85
|
+
end
|
86
|
+
def fetch_latest_version_with_no_unlock(language_version:)
|
87
|
+
fetch_latest_release(language_version: language_version)&.version
|
88
|
+
end
|
90
89
|
|
91
|
-
|
90
|
+
sig do
|
91
|
+
params(language_version: T.nilable(T.any(String, Dependabot::Version)))
|
92
|
+
.returns(T.nilable(Dependabot::Version))
|
93
|
+
end
|
94
|
+
def fetch_lowest_security_fix_version(language_version: nil)
|
95
|
+
fetch_lowest_security_fix_release(language_version: language_version)&.version
|
96
|
+
end
|
92
97
|
|
93
|
-
|
98
|
+
sig do
|
99
|
+
params(language_version: T.nilable(T.any(String, Dependabot::Version)))
|
100
|
+
.returns(T.nilable(Dependabot::Package::PackageRelease))
|
101
|
+
end
|
102
|
+
def fetch_latest_release(language_version: nil) # rubocop:disable Lint/UnusedMethodArgument
|
103
|
+
possible_releases = filter_prerelease_versions(releases)
|
104
|
+
possible_releases = filter_date_based_versions(possible_releases)
|
105
|
+
possible_releases = filter_version_types(possible_releases)
|
106
|
+
possible_releases = filter_ignored_versions(possible_releases)
|
107
|
+
possible_releases = filter_by_cooldown(possible_releases)
|
108
|
+
possible_releases_reverse = possible_releases.reverse
|
109
|
+
|
110
|
+
possible_releases_reverse.find do |r|
|
111
|
+
package_details_fetcher.released?(r.version)
|
112
|
+
end
|
94
113
|
end
|
95
114
|
|
96
|
-
|
115
|
+
sig do
|
116
|
+
params(language_version: T.nilable(T.any(String, Dependabot::Version)))
|
117
|
+
.returns(T.nilable(Dependabot::Package::PackageRelease))
|
118
|
+
end
|
119
|
+
def fetch_lowest_security_fix_release(language_version: nil) # rubocop:disable Lint/UnusedMethodArgument
|
120
|
+
possible_releases = filter_prerelease_versions(releases)
|
121
|
+
possible_releases = filter_date_based_versions(possible_releases)
|
122
|
+
possible_releases = filter_version_types(possible_releases)
|
123
|
+
possible_releases = Dependabot::UpdateCheckers::VersionFilters
|
124
|
+
.filter_vulnerable_versions(
|
125
|
+
possible_releases,
|
126
|
+
security_advisories
|
127
|
+
)
|
128
|
+
possible_releases = filter_ignored_versions(possible_releases)
|
129
|
+
possible_releases = filter_lower_versions(possible_releases)
|
97
130
|
|
98
|
-
|
99
|
-
|
100
|
-
sig { returns(T::Array[Dependabot::DependencyFile]) }
|
101
|
-
attr_reader :dependency_files
|
102
|
-
sig { returns(T::Array[Dependabot::Credential]) }
|
103
|
-
attr_reader :credentials
|
104
|
-
sig { returns(T::Array[String]) }
|
105
|
-
attr_reader :ignored_versions
|
106
|
-
sig { returns(T::Array[String]) }
|
107
|
-
attr_reader :forbidden_urls
|
108
|
-
sig { returns(T::Array[Dependabot::SecurityAdvisory]) }
|
109
|
-
attr_reader :security_advisories
|
131
|
+
possible_releases.find { |r| package_details_fetcher.released?(r.version) }
|
132
|
+
end
|
110
133
|
|
111
|
-
|
112
|
-
def filter_prereleases(possible_versions)
|
113
|
-
return possible_versions if wants_prerelease?
|
134
|
+
private
|
114
135
|
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
136
|
+
sig { returns(Package::PackageDetailsFetcher) }
|
137
|
+
def package_details_fetcher
|
138
|
+
@package_details_fetcher ||= Package::PackageDetailsFetcher.new(
|
139
|
+
dependency: dependency,
|
140
|
+
dependency_files: dependency_files,
|
141
|
+
credentials: credentials
|
142
|
+
)
|
120
143
|
end
|
121
144
|
|
122
|
-
sig
|
145
|
+
sig do
|
146
|
+
params(possible_versions: T::Array[Dependabot::Package::PackageRelease])
|
147
|
+
.returns(T::Array[Dependabot::Package::PackageRelease])
|
148
|
+
end
|
123
149
|
def filter_date_based_versions(possible_versions)
|
124
150
|
return possible_versions if wants_date_based_version?
|
125
151
|
|
126
|
-
filtered = possible_versions.reject { |
|
152
|
+
filtered = possible_versions.reject { |release| release.version > version_class.new(1900) }
|
127
153
|
if possible_versions.count > filtered.count
|
128
154
|
Dependabot.logger.info("Filtered out #{possible_versions.count - filtered.count} date-based versions")
|
129
155
|
end
|
130
156
|
filtered
|
131
157
|
end
|
132
158
|
|
133
|
-
sig
|
159
|
+
sig do
|
160
|
+
params(possible_versions: T::Array[Dependabot::Package::PackageRelease])
|
161
|
+
.returns(T::Array[Dependabot::Package::PackageRelease])
|
162
|
+
end
|
134
163
|
def filter_version_types(possible_versions)
|
135
|
-
filtered = possible_versions.select
|
164
|
+
filtered = possible_versions.select do |release|
|
165
|
+
matches_dependency_version_type?(release.version)
|
166
|
+
end
|
136
167
|
if possible_versions.count > filtered.count
|
137
168
|
diff = possible_versions.count - filtered.count
|
138
169
|
classifier = dependency.version&.split(/[.\-]/)&.last
|
@@ -141,39 +172,6 @@ module Dependabot
|
|
141
172
|
filtered
|
142
173
|
end
|
143
174
|
|
144
|
-
sig { params(possible_versions: T::Array[T.untyped]).returns(T::Array[T.untyped]) }
|
145
|
-
def filter_ignored_versions(possible_versions)
|
146
|
-
filtered = possible_versions
|
147
|
-
|
148
|
-
ignored_versions.each do |req|
|
149
|
-
ignore_requirements = Maven::Requirement.requirements_array(req)
|
150
|
-
filtered =
|
151
|
-
filtered
|
152
|
-
.reject { |v| ignore_requirements.any? { |r| r.satisfied_by?(v.fetch(:version)) } }
|
153
|
-
end
|
154
|
-
|
155
|
-
if @raise_on_ignored && filter_lower_versions(filtered).empty? &&
|
156
|
-
filter_lower_versions(possible_versions).any?
|
157
|
-
raise AllVersionsIgnored
|
158
|
-
end
|
159
|
-
|
160
|
-
if possible_versions.count > filtered.count
|
161
|
-
diff = possible_versions.count - filtered.count
|
162
|
-
Dependabot.logger.info("Filtered out #{diff} ignored versions")
|
163
|
-
end
|
164
|
-
|
165
|
-
filtered
|
166
|
-
end
|
167
|
-
|
168
|
-
sig { params(possible_versions: T::Array[T.untyped]).returns(T::Array[T.untyped]) }
|
169
|
-
def filter_lower_versions(possible_versions)
|
170
|
-
return possible_versions unless dependency.numeric_version
|
171
|
-
|
172
|
-
possible_versions.select do |v|
|
173
|
-
v.fetch(:version) > dependency.numeric_version
|
174
|
-
end
|
175
|
-
end
|
176
|
-
|
177
175
|
sig { returns(T::Boolean) }
|
178
176
|
def wants_prerelease?
|
179
177
|
return false unless dependency.numeric_version
|
@@ -188,124 +186,7 @@ module Dependabot
|
|
188
186
|
T.must(dependency.numeric_version) >= version_class.new(100)
|
189
187
|
end
|
190
188
|
|
191
|
-
sig { params(
|
192
|
-
def released?(version)
|
193
|
-
@released_check[version] ||=
|
194
|
-
repositories.any? do |repository_details|
|
195
|
-
url = repository_details.fetch("url")
|
196
|
-
response = Dependabot::RegistryClient.head(
|
197
|
-
url: dependency_files_url(url, version),
|
198
|
-
headers: repository_details.fetch("auth_headers")
|
199
|
-
)
|
200
|
-
|
201
|
-
response.status < 400
|
202
|
-
rescue Excon::Error::Socket, Excon::Error::Timeout,
|
203
|
-
Excon::Error::TooManyRedirects
|
204
|
-
false
|
205
|
-
rescue URI::InvalidURIError => e
|
206
|
-
raise DependencyFileNotResolvable, e.message
|
207
|
-
end
|
208
|
-
end
|
209
|
-
|
210
|
-
sig { params(repository_details: T::Hash[String, T.untyped]).returns(T.nilable(Nokogiri::XML::Document)) }
|
211
|
-
def dependency_metadata(repository_details)
|
212
|
-
repository_key = repository_details.hash
|
213
|
-
return @dependency_metadata[repository_key] if @dependency_metadata.key?(repository_key)
|
214
|
-
|
215
|
-
xml_document = fetch_dependency_metadata(repository_details)
|
216
|
-
|
217
|
-
@dependency_metadata[repository_key] ||= xml_document if xml_document
|
218
|
-
@dependency_metadata[repository_key]
|
219
|
-
end
|
220
|
-
|
221
|
-
sig { params(repository_details: T::Hash[String, T.untyped]).returns(T.nilable(Nokogiri::XML::Document)) }
|
222
|
-
def fetch_dependency_metadata(repository_details)
|
223
|
-
response = Dependabot::RegistryClient.get(
|
224
|
-
url: dependency_metadata_url(repository_details.fetch("url")),
|
225
|
-
headers: repository_details.fetch("auth_headers")
|
226
|
-
)
|
227
|
-
check_response(response, repository_details.fetch("url"))
|
228
|
-
return unless response.status < 400
|
229
|
-
|
230
|
-
Nokogiri::XML(response.body)
|
231
|
-
rescue URI::InvalidURIError
|
232
|
-
nil
|
233
|
-
rescue Excon::Error::Socket, Excon::Error::Timeout,
|
234
|
-
Excon::Error::TooManyRedirects => e
|
235
|
-
|
236
|
-
if central_repo_urls.include?(repository_details["url"])
|
237
|
-
response_status = response&.status || 0
|
238
|
-
response_body = if response
|
239
|
-
"RegistryError: #{response.status} response status with body #{response.body}"
|
240
|
-
else
|
241
|
-
"RegistryError: #{e.message}"
|
242
|
-
end
|
243
|
-
|
244
|
-
raise RegistryError.new(response_status, response_body)
|
245
|
-
end
|
246
|
-
|
247
|
-
nil
|
248
|
-
end
|
249
|
-
|
250
|
-
sig { params(response: Excon::Response, repository_url: String).void }
|
251
|
-
def check_response(response, repository_url)
|
252
|
-
return unless [401, 403].include?(response.status)
|
253
|
-
return if @forbidden_urls.include?(repository_url)
|
254
|
-
return if central_repo_urls.include?(repository_url)
|
255
|
-
|
256
|
-
@forbidden_urls << repository_url
|
257
|
-
end
|
258
|
-
|
259
|
-
sig { returns(T::Array[T::Hash[String, T.untyped]]) }
|
260
|
-
def repositories
|
261
|
-
return @repositories if @repositories
|
262
|
-
|
263
|
-
@repositories = credentials_repository_details
|
264
|
-
pom_repository_details.each do |repo|
|
265
|
-
@repositories << repo unless @repositories.any? { |r| r["url"] == repo["url"] }
|
266
|
-
end
|
267
|
-
@repositories
|
268
|
-
end
|
269
|
-
|
270
|
-
sig { returns(Maven::FileParser::RepositoriesFinder) }
|
271
|
-
def repository_finder
|
272
|
-
return @repository_finder if @repository_finder
|
273
|
-
|
274
|
-
@repository_finder =
|
275
|
-
Maven::FileParser::RepositoriesFinder.new(
|
276
|
-
pom_fetcher: Maven::FileParser::PomFetcher.new(dependency_files: dependency_files),
|
277
|
-
dependency_files: dependency_files,
|
278
|
-
credentials: credentials
|
279
|
-
)
|
280
|
-
@repository_finder
|
281
|
-
end
|
282
|
-
|
283
|
-
sig { returns(T::Array[T::Hash[String, T.untyped]]) }
|
284
|
-
def pom_repository_details
|
285
|
-
return @pom_repository_details if @pom_repository_details
|
286
|
-
|
287
|
-
@pom_repository_details =
|
288
|
-
repository_finder
|
289
|
-
.repository_urls(pom: pom)
|
290
|
-
.map do |url|
|
291
|
-
{ "url" => url, "auth_headers" => {} }
|
292
|
-
end
|
293
|
-
@pom_repository_details
|
294
|
-
end
|
295
|
-
|
296
|
-
sig { returns(T::Array[T.untyped]) }
|
297
|
-
def credentials_repository_details
|
298
|
-
credentials
|
299
|
-
.select { |cred| cred["type"] == "maven_repository" && cred["url"] }
|
300
|
-
.map do |cred|
|
301
|
-
{
|
302
|
-
"url" => cred.fetch("url").gsub(%r{/+$}, ""),
|
303
|
-
"auth_headers" => auth_headers(cred.fetch("url").gsub(%r{/+$}, ""))
|
304
|
-
}
|
305
|
-
end
|
306
|
-
end
|
307
|
-
|
308
|
-
sig { params(comparison_version: Version).returns(T::Boolean) }
|
189
|
+
sig { params(comparison_version: Dependabot::Version).returns(T::Boolean) }
|
309
190
|
def matches_dependency_version_type?(comparison_version)
|
310
191
|
return true unless dependency.version
|
311
192
|
|
@@ -326,60 +207,10 @@ module Dependabot
|
|
326
207
|
current_type == version_type
|
327
208
|
end
|
328
209
|
|
329
|
-
sig { returns(T.nilable(Dependabot::DependencyFile)) }
|
330
|
-
def pom
|
331
|
-
filename = dependency.requirements.first&.fetch(:file)
|
332
|
-
dependency_files.find { |f| f.name == filename }
|
333
|
-
end
|
334
|
-
|
335
|
-
sig { params(repository_url: String).returns(String) }
|
336
|
-
def dependency_metadata_url(repository_url)
|
337
|
-
group_id, artifact_id = dependency.name.split(":")
|
338
|
-
|
339
|
-
"#{repository_url}/" \
|
340
|
-
"#{group_id&.tr('.', '/')}/" \
|
341
|
-
"#{artifact_id}/" \
|
342
|
-
"maven-metadata.xml"
|
343
|
-
end
|
344
|
-
|
345
|
-
sig { params(repository_url: String, version: Version).returns(String) }
|
346
|
-
def dependency_files_url(repository_url, version)
|
347
|
-
group_id, artifact_id = dependency.name.split(":")
|
348
|
-
type = dependency.requirements.first&.dig(:metadata, :packaging_type)
|
349
|
-
classifier = dependency.requirements.first&.dig(:metadata, :classifier)
|
350
|
-
|
351
|
-
actual_classifier = classifier.nil? ? "" : "-#{classifier}"
|
352
|
-
"#{repository_url}/" \
|
353
|
-
"#{group_id&.tr('.', '/')}/" \
|
354
|
-
"#{artifact_id}/" \
|
355
|
-
"#{version}/" \
|
356
|
-
"#{artifact_id}-#{version}#{actual_classifier}.#{type}"
|
357
|
-
end
|
358
|
-
|
359
210
|
sig { returns(T.class_of(Dependabot::Version)) }
|
360
211
|
def version_class
|
361
212
|
dependency.version_class
|
362
213
|
end
|
363
|
-
|
364
|
-
sig { returns(T::Array[String]) }
|
365
|
-
def central_repo_urls
|
366
|
-
central_url_without_protocol = repository_finder.central_repo_url.gsub(%r{^.*://}, "")
|
367
|
-
|
368
|
-
%w(http:// https://).map { |p| p + central_url_without_protocol }
|
369
|
-
end
|
370
|
-
|
371
|
-
sig { returns(Utils::AuthHeadersFinder) }
|
372
|
-
def auth_headers_finder
|
373
|
-
return @auth_headers_finder if @auth_headers_finder
|
374
|
-
|
375
|
-
@auth_headers_finder = Utils::AuthHeadersFinder.new(credentials)
|
376
|
-
@auth_headers_finder
|
377
|
-
end
|
378
|
-
|
379
|
-
sig { params(maven_repo_url: String).returns(T::Hash[String, String]) }
|
380
|
-
def auth_headers(maven_repo_url)
|
381
|
-
auth_headers_finder.auth_headers(maven_repo_url)
|
382
|
-
end
|
383
214
|
end
|
384
215
|
end
|
385
216
|
end
|