dependabot-go_modules 0.120.2 → 0.121.1
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:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d399469f8a61821f96b70b4665ef9037c9c103194ae3aa7224fa7bbf45e19cc6
|
4
|
+
data.tar.gz: 041406a7f88713b93f2c91b3fcf903934037975c82a8a7facebc9849baba4488
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: df43946eea402a831d37a56637c69afe605b0c7ea3ad8e387d5e74175b13f629861b71073f7e0548b5630025089bdbc3fd8f7f8d6d00f6a9a08f9b20d96f84b9
|
7
|
+
data.tar.gz: beb0a877aa9c40b20d499da92c26aa03ebfdb9737e61ca1d296bbbb02ead76ec5ab2f953b3430cb7051de9a8bc58405ee6e0ddb105fe1b43f30136850e231594
|
@@ -17,23 +17,31 @@ module Dependabot
|
|
17
17
|
private
|
18
18
|
|
19
19
|
def fetch_files
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
20
|
+
# Ensure we always check out the full repo contents for go_module
|
21
|
+
# updates.
|
22
|
+
SharedHelpers.in_a_temporary_repo_directory(
|
23
|
+
directory,
|
24
|
+
clone_repo_contents
|
25
|
+
) do
|
26
|
+
unless go_mod
|
27
|
+
raise(
|
28
|
+
Dependabot::DependencyFileNotFound,
|
29
|
+
Pathname.new(File.join(directory, "go.mod")).
|
30
|
+
cleanpath.to_path
|
31
|
+
)
|
32
|
+
end
|
33
|
+
|
34
|
+
fetched_files = [go_mod]
|
35
|
+
|
36
|
+
# Fetch the (optional) go.sum
|
37
|
+
fetched_files << go_sum if go_sum
|
38
|
+
|
39
|
+
# Fetch the main.go file if present, as this will later identify
|
40
|
+
# this repo as an app.
|
41
|
+
fetched_files << main if main
|
42
|
+
|
43
|
+
fetched_files
|
25
44
|
end
|
26
|
-
|
27
|
-
fetched_files = [go_mod]
|
28
|
-
|
29
|
-
# Fetch the (optional) go.sum
|
30
|
-
fetched_files << go_sum if go_sum
|
31
|
-
|
32
|
-
# Fetch the main.go file if present, as this will later identify
|
33
|
-
# this repo as an app.
|
34
|
-
fetched_files << main if main
|
35
|
-
|
36
|
-
fetched_files
|
37
45
|
end
|
38
46
|
|
39
47
|
def go_mod
|
@@ -45,15 +53,21 @@ module Dependabot
|
|
45
53
|
end
|
46
54
|
|
47
55
|
def main
|
48
|
-
return @main if @main
|
56
|
+
return @main if defined?(@main)
|
49
57
|
|
50
|
-
go_files =
|
58
|
+
go_files = Dir.glob("*.go")
|
51
59
|
|
52
|
-
go_files.each do |
|
53
|
-
|
54
|
-
next unless
|
60
|
+
go_files.each do |filename|
|
61
|
+
file_content = File.read(filename)
|
62
|
+
next unless file_content.match?(/\s*package\s+main/)
|
55
63
|
|
56
|
-
return @main =
|
64
|
+
return @main = DependencyFile.new(
|
65
|
+
name: Pathname.new(filename).cleanpath.to_path,
|
66
|
+
directory: "/",
|
67
|
+
type: "package_main",
|
68
|
+
support_file: true,
|
69
|
+
content: file_content
|
70
|
+
)
|
57
71
|
end
|
58
72
|
|
59
73
|
nil
|
@@ -9,6 +9,27 @@ module Dependabot
|
|
9
9
|
class FileUpdater < Dependabot::FileUpdaters::Base
|
10
10
|
require_relative "file_updater/go_mod_updater"
|
11
11
|
|
12
|
+
def initialize(dependencies:, dependency_files:, repo_contents_path: nil,
|
13
|
+
credentials:, options: {})
|
14
|
+
super
|
15
|
+
return unless repo_contents_path.nil?
|
16
|
+
|
17
|
+
# masquerade repo_contents_path for GoModUpdater during transition
|
18
|
+
tmp = Dir.mktmpdir
|
19
|
+
Dir.chdir(tmp) do
|
20
|
+
dependency_files.each do |file|
|
21
|
+
File.write(file.name, file.content)
|
22
|
+
end
|
23
|
+
`git config --global user.email "no-reply@github.com"`
|
24
|
+
`git config --global user.name "Dependabot"`
|
25
|
+
`git init .`
|
26
|
+
`git add .`
|
27
|
+
`git commit -m'fake repo_contents_path'`
|
28
|
+
end
|
29
|
+
@repo_contents_path = tmp
|
30
|
+
@repo_contents_stub = true
|
31
|
+
end
|
32
|
+
|
12
33
|
def self.updated_files_regex
|
13
34
|
[
|
14
35
|
/^go\.mod$/,
|
@@ -56,13 +77,18 @@ module Dependabot
|
|
56
77
|
@go_sum ||= get_original_file("go.sum")
|
57
78
|
end
|
58
79
|
|
80
|
+
def directory
|
81
|
+
dependency_files.first.directory
|
82
|
+
end
|
83
|
+
|
59
84
|
def file_updater
|
60
85
|
@file_updater ||=
|
61
86
|
GoModUpdater.new(
|
62
87
|
dependencies: dependencies,
|
63
|
-
|
64
|
-
|
65
|
-
|
88
|
+
credentials: credentials,
|
89
|
+
repo_contents_path: repo_contents_path,
|
90
|
+
directory: directory,
|
91
|
+
tidy: !@repo_contents_stub && options.fetch(:go_mod_tidy, false)
|
66
92
|
)
|
67
93
|
end
|
68
94
|
end
|
@@ -25,11 +25,13 @@ module Dependabot
|
|
25
25
|
/go: ([^@\s]+)(?:@[^\s]+)?: .* declares its path as: ([\S]*)/m
|
26
26
|
].freeze
|
27
27
|
|
28
|
-
def initialize(dependencies:,
|
28
|
+
def initialize(dependencies:, credentials:, repo_contents_path:,
|
29
|
+
directory:, tidy:)
|
29
30
|
@dependencies = dependencies
|
30
|
-
@go_mod = go_mod
|
31
|
-
@go_sum = go_sum
|
32
31
|
@credentials = credentials
|
32
|
+
@repo_contents_path = repo_contents_path
|
33
|
+
@directory = directory
|
34
|
+
@tidy = tidy
|
33
35
|
end
|
34
36
|
|
35
37
|
def updated_go_mod_content
|
@@ -42,64 +44,74 @@ module Dependabot
|
|
42
44
|
|
43
45
|
private
|
44
46
|
|
45
|
-
attr_reader :dependencies, :
|
47
|
+
attr_reader :dependencies, :credentials, :repo_contents_path,
|
48
|
+
:directory
|
46
49
|
|
47
50
|
def updated_files
|
48
51
|
@updated_files ||= update_files
|
49
52
|
end
|
50
53
|
|
51
|
-
# rubocop:disable Metrics/AbcSize
|
52
54
|
def update_files
|
53
|
-
|
54
|
-
|
55
|
-
stub_dirs = substitutions.values
|
55
|
+
in_repo_path do
|
56
|
+
# Map paths in local replace directives to path hashes
|
56
57
|
|
57
|
-
|
58
|
-
|
58
|
+
original_go_mod = File.read("go.mod")
|
59
|
+
original_manifest = parse_manifest
|
60
|
+
original_go_sum = File.read("go.sum") if File.exist?("go.sum")
|
59
61
|
|
60
|
-
|
61
|
-
|
62
|
-
update_go_mod(clean_go_mod, dependencies)
|
63
|
-
end
|
62
|
+
substitutions = replace_directive_substitutions(original_manifest)
|
63
|
+
build_module_stubs(substitutions.values)
|
64
64
|
|
65
|
-
|
66
|
-
|
67
|
-
regenerated_files = in_temp_dir(stub_dirs) do
|
68
|
-
run_go_get(updated_go_mod, go_sum)
|
69
|
-
end
|
65
|
+
# Replace full paths with path hashes in the go.mod
|
66
|
+
substitute_all(substitutions)
|
70
67
|
|
71
|
-
|
72
|
-
|
73
|
-
# undesirable ways (such as injecting the current Go version), so we
|
74
|
-
# need to update the original go.mod with the updated set of
|
75
|
-
# requirements rather than using the regenerated file directly
|
76
|
-
original_reqs = in_temp_dir(stub_dirs) do
|
77
|
-
parse_manifest_requirements(go_mod.content)
|
78
|
-
end
|
79
|
-
updated_reqs = in_temp_dir(stub_dirs) do
|
80
|
-
parse_manifest_requirements(regenerated_files[:go_mod])
|
81
|
-
end
|
68
|
+
# Set the stubbed replace directives
|
69
|
+
update_go_mod(dependencies)
|
82
70
|
|
83
|
-
|
84
|
-
|
85
|
-
|
71
|
+
# Then run `go get` to pick up other changes to the file caused by
|
72
|
+
# the upgrade
|
73
|
+
run_go_get
|
74
|
+
run_go_mod_tidy
|
86
75
|
|
87
|
-
|
88
|
-
|
89
|
-
|
76
|
+
# At this point, the go.mod returned from run_go_get contains the
|
77
|
+
# correct set of modules, but running `go get` can change the file
|
78
|
+
# in undesirable ways (such as injecting the current Go version),
|
79
|
+
# so we need to update the original go.mod with the updated set of
|
80
|
+
# requirements rather than using the regenerated file directly
|
81
|
+
original_reqs = original_manifest["Require"] || []
|
82
|
+
updated_reqs = parse_manifest["Require"] || []
|
90
83
|
|
91
|
-
|
84
|
+
original_paths = original_reqs.map { |r| r["Path"] }
|
85
|
+
updated_paths = updated_reqs.map { |r| r["Path"] }
|
86
|
+
req_paths_to_remove = original_paths - updated_paths
|
87
|
+
|
88
|
+
# Put back the original content before we replace just the updated
|
89
|
+
# dependencies.
|
90
|
+
write_go_mod(original_go_mod)
|
91
|
+
|
92
|
+
remove_requirements(req_paths_to_remove)
|
92
93
|
deps = updated_reqs.map { |r| requirement_to_dependency_obj(r) }
|
93
|
-
update_go_mod(
|
94
|
-
|
94
|
+
update_go_mod(deps)
|
95
|
+
|
96
|
+
# put the old replace directives back again
|
97
|
+
substitute_all(substitutions.invert)
|
95
98
|
|
96
|
-
|
99
|
+
updated_go_sum = original_go_sum ? File.read("go.sum") : nil
|
100
|
+
updated_go_mod = File.read("go.mod")
|
101
|
+
|
102
|
+
{ go_mod: updated_go_mod, go_sum: updated_go_sum }
|
103
|
+
end
|
97
104
|
end
|
98
|
-
# rubocop:enable Metrics/AbcSize
|
99
105
|
|
100
|
-
def
|
101
|
-
|
106
|
+
def run_go_mod_tidy
|
107
|
+
return unless tidy?
|
108
|
+
|
109
|
+
command = "go mod tidy"
|
110
|
+
_, stderr, status = Open3.capture3(ENVIRONMENT, command)
|
111
|
+
handle_subprocess_error(stderr) unless status.success?
|
112
|
+
end
|
102
113
|
|
114
|
+
def update_go_mod(dependencies)
|
103
115
|
deps = dependencies.map do |dep|
|
104
116
|
{
|
105
117
|
name: dep.name,
|
@@ -108,78 +120,75 @@ module Dependabot
|
|
108
120
|
}
|
109
121
|
end
|
110
122
|
|
111
|
-
SharedHelpers.run_helper_subprocess(
|
123
|
+
body = SharedHelpers.run_helper_subprocess(
|
112
124
|
command: NativeHelpers.helper_path,
|
113
125
|
env: ENVIRONMENT,
|
114
126
|
function: "updateDependencyFile",
|
115
127
|
args: { dependencies: deps }
|
116
128
|
)
|
129
|
+
|
130
|
+
write_go_mod(body)
|
117
131
|
end
|
118
132
|
|
119
|
-
def run_go_get
|
120
|
-
|
121
|
-
|
122
|
-
|
133
|
+
def run_go_get
|
134
|
+
tmp_go_file = "#{SecureRandom.hex}.go"
|
135
|
+
|
136
|
+
unless Dir.glob("*.go").any?
|
137
|
+
File.write(tmp_go_file, "package dummypkg\n")
|
138
|
+
end
|
123
139
|
|
124
140
|
_, stderr, status = Open3.capture3(ENVIRONMENT, "go get -d")
|
125
141
|
handle_subprocess_error(stderr) unless status.success?
|
126
|
-
|
127
|
-
|
128
|
-
{ go_mod: File.read("go.mod"), go_sum: updated_go_sum }
|
142
|
+
ensure
|
143
|
+
File.delete(tmp_go_file) if File.exist?(tmp_go_file)
|
129
144
|
end
|
130
145
|
|
131
|
-
def
|
132
|
-
File.write("go.mod", go_mod_content)
|
133
|
-
|
146
|
+
def parse_manifest
|
134
147
|
command = "go mod edit -json"
|
135
148
|
stdout, stderr, status = Open3.capture3(ENVIRONMENT, command)
|
136
149
|
handle_subprocess_error(stderr) unless status.success?
|
137
150
|
|
138
|
-
JSON.parse(stdout)
|
151
|
+
JSON.parse(stdout) || {}
|
139
152
|
end
|
140
153
|
|
141
|
-
def remove_requirements(
|
142
|
-
File.write("go.mod", go_mod_content)
|
143
|
-
|
154
|
+
def remove_requirements(requirement_paths)
|
144
155
|
requirement_paths.each do |path|
|
145
156
|
escaped_path = Shellwords.escape(path)
|
146
157
|
command = "go mod edit -droprequire #{escaped_path}"
|
147
158
|
_, stderr, status = Open3.capture3(ENVIRONMENT, command)
|
148
159
|
handle_subprocess_error(stderr) unless status.success?
|
149
160
|
end
|
150
|
-
|
151
|
-
File.read("go.mod")
|
152
161
|
end
|
153
162
|
|
154
|
-
def add_requirements(
|
155
|
-
File.write("go.mod", go_mod_content)
|
156
|
-
|
163
|
+
def add_requirements(requirements)
|
157
164
|
requirements.each do |r|
|
158
165
|
escaped_req = Shellwords.escape("#{r['Path']}@#{r['Version']}")
|
159
166
|
command = "go mod edit -require #{escaped_req}"
|
160
167
|
_, stderr, status = Open3.capture3(ENVIRONMENT, command)
|
161
168
|
handle_subprocess_error(stderr) unless status.success?
|
162
169
|
end
|
163
|
-
|
164
|
-
File.read("go.mod")
|
165
170
|
end
|
166
171
|
|
167
|
-
def
|
168
|
-
SharedHelpers.
|
172
|
+
def in_repo_path(&block)
|
173
|
+
SharedHelpers.
|
174
|
+
in_a_temporary_repo_directory(directory, repo_contents_path) do
|
169
175
|
SharedHelpers.with_git_configured(credentials: credentials) do
|
170
|
-
# Create a fake empty module for each local module so that
|
171
|
-
# `go get -d` works, even if some modules have been `replace`d
|
172
|
-
# with a local module that we don't have access to.
|
173
|
-
stub_paths.each do |stub_path|
|
174
|
-
Dir.mkdir(stub_path) unless Dir.exist?(stub_path)
|
175
|
-
FileUtils.touch(File.join(stub_path, "go.mod"))
|
176
|
-
end
|
177
|
-
|
178
176
|
block.call
|
179
177
|
end
|
180
178
|
end
|
181
179
|
end
|
182
180
|
|
181
|
+
def build_module_stubs(stub_paths)
|
182
|
+
# Create a fake empty module for each local module so that
|
183
|
+
# `go get -d` works, even if some modules have been `replace`d
|
184
|
+
# with a local module that we don't have access to.
|
185
|
+
stub_paths.each do |stub_path|
|
186
|
+
Dir.mkdir(stub_path) unless Dir.exist?(stub_path)
|
187
|
+
FileUtils.touch(File.join(stub_path, "go.mod"))
|
188
|
+
FileUtils.touch(File.join(stub_path, "main.go"))
|
189
|
+
end
|
190
|
+
end
|
191
|
+
|
183
192
|
# Given a go.mod file, find all `replace` directives pointing to a path
|
184
193
|
# on the local filesystem, and return an array of pairs mapping the
|
185
194
|
# original path to a hash of the path.
|
@@ -188,22 +197,14 @@ module Dependabot
|
|
188
197
|
# the layout of the filesystem with a structure we can reproduce (i.e.
|
189
198
|
# no paths such as ../../../foo), run the Go tooling, then reverse the
|
190
199
|
# process afterwards.
|
191
|
-
def replace_directive_substitutions(
|
200
|
+
def replace_directive_substitutions(manifest)
|
192
201
|
@replace_directive_substitutions ||=
|
193
|
-
|
194
|
-
File.write("go.mod", go_mod_content)
|
195
|
-
|
196
|
-
# Parse the go.mod to get a JSON representation of the replace
|
197
|
-
# directives
|
198
|
-
command = "go mod edit -json"
|
199
|
-
stdout, stderr, status = Open3.capture3(ENVIRONMENT, command)
|
200
|
-
handle_subprocess_error(path, stderr) unless status.success?
|
201
|
-
|
202
|
+
begin
|
202
203
|
# Find all the local replacements, and return them with a stub
|
203
204
|
# path we can use in their place. Using generated paths is safer
|
204
205
|
# as it means we don't need to worry about references to parent
|
205
206
|
# directories, etc.
|
206
|
-
(
|
207
|
+
(manifest["Replace"] || []).
|
207
208
|
map { |r| r["New"]["Path"] }.
|
208
209
|
compact.
|
209
210
|
select { |p| p.start_with?(".") || p.start_with?("/") }.
|
@@ -212,10 +213,12 @@ module Dependabot
|
|
212
213
|
end
|
213
214
|
end
|
214
215
|
|
215
|
-
def substitute_all(
|
216
|
-
substitutions.reduce(
|
216
|
+
def substitute_all(substitutions)
|
217
|
+
body = substitutions.reduce(File.read("go.mod")) do |text, (a, b)|
|
217
218
|
text.sub(a, b)
|
218
219
|
end
|
220
|
+
|
221
|
+
write_go_mod(body)
|
219
222
|
end
|
220
223
|
|
221
224
|
def handle_subprocess_error(stderr)
|
@@ -231,28 +234,18 @@ module Dependabot
|
|
231
234
|
if path_regex
|
232
235
|
match = path_regex.match(stderr)
|
233
236
|
raise Dependabot::GoModulePathMismatch.
|
234
|
-
new(
|
237
|
+
new(go_mod_path, match[1], match[2])
|
235
238
|
end
|
236
239
|
|
237
240
|
msg = stderr.lines.last(10).join.strip
|
238
|
-
raise Dependabot::DependencyFileNotParseable.
|
241
|
+
raise Dependabot::DependencyFileNotParseable.
|
242
|
+
new(go_mod_path, msg)
|
239
243
|
end
|
240
244
|
|
241
|
-
def
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
# package, we have no way of working out the import path, so the
|
246
|
-
# build step fails.
|
247
|
-
#
|
248
|
-
# In due course, if we end up fetching the full repo, it might be
|
249
|
-
# good to switch back to `main` so we can surface more errors.
|
250
|
-
lines = ["package dummypkg", "import ("]
|
251
|
-
dependencies.each do |dep|
|
252
|
-
lines << "_ \"#{dep.name}\"" unless dep.requirements.empty?
|
253
|
-
end
|
254
|
-
lines << ")"
|
255
|
-
lines.join("\n")
|
245
|
+
def go_mod_path
|
246
|
+
return "go.mod" if directory == "/"
|
247
|
+
|
248
|
+
File.join(directory, "go.mod")
|
256
249
|
end
|
257
250
|
|
258
251
|
def requirement_to_dependency_obj(req)
|
@@ -272,6 +265,14 @@ module Dependabot
|
|
272
265
|
package_manager: "go_modules"
|
273
266
|
)
|
274
267
|
end
|
268
|
+
|
269
|
+
def write_go_mod(body)
|
270
|
+
File.write("go.mod", body)
|
271
|
+
end
|
272
|
+
|
273
|
+
def tidy?
|
274
|
+
!!@tidy
|
275
|
+
end
|
275
276
|
end
|
276
277
|
end
|
277
278
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: dependabot-go_modules
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.121.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Dependabot
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-
|
11
|
+
date: 2020-10-07 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: dependabot-common
|
@@ -16,14 +16,14 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - '='
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 0.
|
19
|
+
version: 0.121.1
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
24
|
- - '='
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: 0.
|
26
|
+
version: 0.121.1
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: byebug
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
@@ -100,14 +100,14 @@ dependencies:
|
|
100
100
|
requirements:
|
101
101
|
- - "~>"
|
102
102
|
- !ruby/object:Gem::Version
|
103
|
-
version: 0.
|
103
|
+
version: 0.92.0
|
104
104
|
type: :development
|
105
105
|
prerelease: false
|
106
106
|
version_requirements: !ruby/object:Gem::Requirement
|
107
107
|
requirements:
|
108
108
|
- - "~>"
|
109
109
|
- !ruby/object:Gem::Version
|
110
|
-
version: 0.
|
110
|
+
version: 0.92.0
|
111
111
|
- !ruby/object:Gem::Dependency
|
112
112
|
name: vcr
|
113
113
|
requirement: !ruby/object:Gem::Requirement
|