dependabot-python 0.358.0 → 0.359.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 48c37437d99c146971cb9ecc12889faf559a657346ca44b95a71bc06d607445a
4
- data.tar.gz: 163fbc7bfcb2aecde6cbc0f95bdc33bb1cb454201b6014158a65dcc71ab22fc4
3
+ metadata.gz: 9b809922cec5a45858a2db5ccbc1a44616bd29e338b208ef2ce62c40cc92c5cc
4
+ data.tar.gz: 690573daf64882e4308e2b67962d218b050d6e35f5f2de463037c9d3bb4373f5
5
5
  SHA512:
6
- metadata.gz: de34134537d989cc22bdea97b581b80e0adf85cde617690689916fbc1169e462d1fdea9c9c40369401ac2edcf4cf21015d3c399c9b4ebaafaf0fa9541109f84f
7
- data.tar.gz: bf298b6e70c2fd083f89d3186a31d610ac937fe749345974edcce57f5871f97579bd215e3d5897f1b6d82e691a7a400f287c3d97241b50249d73dab2f2b1e765
6
+ metadata.gz: 85cbac2d3e04004f10fb8829b512c22962339aca71b3e2fe00b5b22a0af1a745cc6a0810d038f5bf084dcebd749959fb73bcf08408de67a5683a61d7eb47e121
7
+ data.tar.gz: f2336e9490af88f4a08ed69c4116b085d161e2e0e8ef5ea5e2e494fb1308ea5b62239761a675c4f214cd79b943a0414d7e2133a6a5e5573b4aac1ef433723a8a
@@ -180,10 +180,14 @@ module Dependabot
180
180
  }
181
181
  else
182
182
  check_requirements(requirement)
183
+ # String sources are registry name references (e.g., "custom") that reference
184
+ # [[tool.poetry.source]] definitions. Resolve them to proper hashes.
185
+ source_value = requirement.fetch("source", nil)
186
+ source = resolve_source(source_value)
183
187
  {
184
188
  requirement: requirement["version"],
185
189
  file: T.must(pyproject).name,
186
- source: requirement.fetch("source", nil),
190
+ source: source,
187
191
  groups: [type]
188
192
  }
189
193
  end
@@ -299,6 +303,34 @@ module Dependabot
299
303
  NameNormaliser.normalise(name)
300
304
  end
301
305
 
306
+ sig { params(source_value: T.untyped).returns(T.nilable(T::Hash[Symbol, T.untyped])) }
307
+ def resolve_source(source_value)
308
+ # Return nil if no source specified
309
+ return nil if source_value.nil?
310
+
311
+ # If already a hash, return as-is (handles git sources)
312
+ return source_value if source_value.is_a?(Hash)
313
+
314
+ # String sources are references to [[tool.poetry.source]] definitions
315
+ # Look up the source definition and create a hash
316
+ return nil unless source_value.is_a?(String)
317
+
318
+ source_name = source_value
319
+ poetry_sources = parsed_pyproject.dig("tool", "poetry", "source") || []
320
+ source_def = poetry_sources.find { |s| s["name"] == source_name }
321
+
322
+ # If source definition not found, return nil
323
+ return nil unless source_def
324
+
325
+ # Create a hash with type and url from the source definition
326
+ # Use "registry" as the type since these are package index sources
327
+ {
328
+ type: "registry",
329
+ url: source_def["url"],
330
+ name: source_name
331
+ }
332
+ end
333
+
302
334
  sig { returns(T.untyped) }
303
335
  def parsed_pyproject
304
336
  @parsed_pyproject ||= T.let(TomlRB.parse(T.must(pyproject).content), T.untyped)
@@ -1,4 +1,4 @@
1
- # typed: strong
1
+ # typed: strict
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require "cgi"
@@ -7,6 +7,7 @@ require "nokogiri"
7
7
  require "sorbet-runtime"
8
8
 
9
9
  require "dependabot/dependency"
10
+ require "dependabot/git_commit_checker"
10
11
  require "dependabot/python/update_checker"
11
12
  require "dependabot/update_checkers/version_filters"
12
13
  require "dependabot/registry_client"
@@ -22,6 +23,38 @@ module Dependabot
22
23
  class LatestVersionFinder < Dependabot::Package::PackageLatestVersionFinder
23
24
  extend T::Sig
24
25
 
26
+ sig do
27
+ params(git_commit_checker: Dependabot::GitCommitChecker)
28
+ .returns(T.nilable(T::Hash[Symbol, T.untyped]))
29
+ end
30
+ def latest_version_tag(git_commit_checker:)
31
+ return git_commit_checker.local_tag_for_latest_version unless cooldown_enabled?
32
+
33
+ allowed_version_tags = git_commit_checker.local_tags_for_allowed_versions
34
+ tags_in_cooldown = select_version_tags_in_cooldown_period(git_commit_checker)
35
+
36
+ return max_version_from_tags(allowed_version_tags) if tags_in_cooldown.empty?
37
+
38
+ filtered_tags = allowed_version_tags.reject do |tag|
39
+ tags_in_cooldown.include?(tag[:tag])
40
+ end
41
+
42
+ if filtered_tags.empty?
43
+ Dependabot.logger.info("All git tags filtered by cooldown for #{dependency.name}, returning nil")
44
+ return nil
45
+ end
46
+
47
+ filtered_count = allowed_version_tags.count - filtered_tags.count
48
+ if filtered_count.positive?
49
+ Dependabot.logger.info("Filtered #{filtered_count} git tags due to cooldown for #{dependency.name}")
50
+ end
51
+
52
+ max_version_from_tags(filtered_tags)
53
+ rescue StandardError => e
54
+ Dependabot.logger.error("Error fetching latest version tag: #{e.message}")
55
+ git_commit_checker.local_tag_for_latest_version
56
+ end
57
+
25
58
  sig do
26
59
  override.returns(T.nilable(Dependabot::Package::PackageDetails))
27
60
  end
@@ -35,7 +68,93 @@ module Dependabot
35
68
 
36
69
  sig { override.returns(T::Boolean) }
37
70
  def cooldown_enabled?
38
- true
71
+ return false if cooldown_options.nil?
72
+
73
+ cooldown = T.must(cooldown_options)
74
+ cooldown.default_days.to_i.positive? ||
75
+ cooldown.semver_major_days.to_i.positive? ||
76
+ cooldown.semver_minor_days.to_i.positive? ||
77
+ cooldown.semver_patch_days.to_i.positive?
78
+ end
79
+
80
+ private
81
+
82
+ sig { params(tags: T::Array[T::Hash[Symbol, T.untyped]]).returns(T.nilable(T::Hash[Symbol, T.untyped])) }
83
+ def max_version_from_tags(tags)
84
+ tags.max_by { |t| t[:version] }
85
+ end
86
+
87
+ sig { params(git_commit_checker: Dependabot::GitCommitChecker).returns(T::Array[String]) }
88
+ def select_version_tags_in_cooldown_period(git_commit_checker)
89
+ version_tags_in_cooldown_period = T.let([], T::Array[String])
90
+
91
+ git_commit_checker.refs_for_tag_with_detail.each do |git_tag_with_detail|
92
+ if check_if_version_in_cooldown_period?(git_tag_with_detail)
93
+ version_tags_in_cooldown_period << git_tag_with_detail.tag
94
+ end
95
+ end
96
+ version_tags_in_cooldown_period
97
+ rescue StandardError => e
98
+ Dependabot.logger.error("Error checking if version is in cooldown: #{e.message}")
99
+ []
100
+ end
101
+
102
+ sig { params(tag_with_detail: Dependabot::GitTagWithDetail).returns(T::Boolean) }
103
+ def check_if_version_in_cooldown_period?(tag_with_detail)
104
+ return false unless tag_with_detail.release_date
105
+
106
+ current_version = version_class.correct?(dependency.version) ? version_class.new(dependency.version) : nil
107
+ tag_version_str = tag_with_detail.tag.delete_prefix("v")
108
+ return false unless version_class.correct?(tag_version_str)
109
+
110
+ new_version = version_class.new(tag_version_str)
111
+ days = cooldown_days_for(current_version, new_version)
112
+
113
+ passed_seconds = Time.now.to_i - release_date_to_seconds(tag_with_detail.release_date)
114
+ passed_seconds < days * DAY_IN_SECONDS
115
+ end
116
+
117
+ sig do
118
+ params(
119
+ current_version: T.nilable(Dependabot::Version),
120
+ new_version: Dependabot::Version
121
+ ).returns(Integer)
122
+ end
123
+ def cooldown_days_for(current_version, new_version)
124
+ return 0 unless cooldown_enabled?
125
+
126
+ cooldown = T.must(cooldown_options)
127
+ return 0 unless cooldown.included?(dependency.name)
128
+ return cooldown.default_days if current_version.nil?
129
+
130
+ current_version_semver = current_version.semver_parts
131
+ new_version_semver = new_version.semver_parts
132
+
133
+ return cooldown.default_days if current_version_semver.nil? || new_version_semver.nil?
134
+
135
+ current_major, current_minor, current_patch = current_version_semver
136
+ new_major, new_minor, new_patch = new_version_semver
137
+
138
+ return cooldown.semver_major_days if new_major > current_major
139
+ return cooldown.semver_minor_days if new_minor > current_minor
140
+ return cooldown.semver_patch_days if new_patch > current_patch
141
+
142
+ cooldown.default_days
143
+ end
144
+
145
+ sig { returns(T.class_of(Dependabot::Version)) }
146
+ def version_class
147
+ dependency.version_class
148
+ end
149
+
150
+ sig { params(release_date: T.nilable(String)).returns(Integer) }
151
+ def release_date_to_seconds(release_date)
152
+ return 0 unless release_date
153
+
154
+ Time.parse(release_date).to_i
155
+ rescue ArgumentError => e
156
+ Dependabot.logger.error("Invalid release date format: #{release_date} and error: #{e.message}")
157
+ 0
39
158
  end
40
159
  end
41
160
  end
@@ -163,7 +163,7 @@ module Dependabot
163
163
  sig { returns(T.nilable(T::Hash[Symbol, T.untyped])) }
164
164
  def latest_git_version_details
165
165
  @latest_git_version_details ||= T.let(
166
- git_commit_checker.local_tag_for_latest_version,
166
+ latest_version_finder.latest_version_tag(git_commit_checker: git_commit_checker),
167
167
  T.nilable(T::Hash[Symbol, T.untyped])
168
168
  )
169
169
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dependabot-python
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.358.0
4
+ version: 0.359.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dependabot
@@ -15,14 +15,14 @@ dependencies:
15
15
  requirements:
16
16
  - - '='
17
17
  - !ruby/object:Gem::Version
18
- version: 0.358.0
18
+ version: 0.359.0
19
19
  type: :runtime
20
20
  prerelease: false
21
21
  version_requirements: !ruby/object:Gem::Requirement
22
22
  requirements:
23
23
  - - '='
24
24
  - !ruby/object:Gem::Version
25
- version: 0.358.0
25
+ version: 0.359.0
26
26
  - !ruby/object:Gem::Dependency
27
27
  name: debug
28
28
  requirement: !ruby/object:Gem::Requirement
@@ -291,7 +291,7 @@ licenses:
291
291
  - MIT
292
292
  metadata:
293
293
  bug_tracker_uri: https://github.com/dependabot/dependabot-core/issues
294
- changelog_uri: https://github.com/dependabot/dependabot-core/releases/tag/v0.358.0
294
+ changelog_uri: https://github.com/dependabot/dependabot-core/releases/tag/v0.359.0
295
295
  rdoc_options: []
296
296
  require_paths:
297
297
  - lib