r10k 3.13.0 → 3.14.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 (41) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/docker.yml +1 -1
  3. data/.github/workflows/rspec_tests.yml +2 -2
  4. data/.travis.yml +1 -1
  5. data/CHANGELOG.mkd +10 -0
  6. data/doc/dynamic-environments/configuration.mkd +24 -0
  7. data/doc/puppetfile.mkd +13 -0
  8. data/lib/r10k/environment/name.rb +14 -9
  9. data/lib/r10k/environment/tarball.rb +78 -0
  10. data/lib/r10k/environment.rb +1 -0
  11. data/lib/r10k/forge/module_release.rb +2 -1
  12. data/lib/r10k/git/cache.rb +4 -13
  13. data/lib/r10k/git/rugged/base_repository.rb +12 -1
  14. data/lib/r10k/git/rugged/cache.rb +8 -0
  15. data/lib/r10k/git/stateful_repository.rb +2 -0
  16. data/lib/r10k/initializers.rb +10 -0
  17. data/lib/r10k/module/tarball.rb +101 -0
  18. data/lib/r10k/module.rb +1 -0
  19. data/lib/r10k/module_loader/puppetfile.rb +10 -1
  20. data/lib/r10k/source/git.rb +18 -18
  21. data/lib/r10k/tarball.rb +183 -0
  22. data/lib/r10k/util/cacheable.rb +31 -0
  23. data/lib/r10k/util/downloader.rb +134 -0
  24. data/lib/r10k/version.rb +1 -1
  25. data/locales/r10k.pot +39 -23
  26. data/r10k.gemspec +2 -2
  27. data/spec/fixtures/tarball/tarball.tar.gz +0 -0
  28. data/spec/integration/git/rugged/cache_spec.rb +33 -0
  29. data/spec/shared-contexts/tarball.rb +32 -0
  30. data/spec/spec_helper.rb +1 -0
  31. data/spec/unit/action/deploy/module_spec.rb +2 -2
  32. data/spec/unit/environment/name_spec.rb +18 -0
  33. data/spec/unit/environment/tarball_spec.rb +45 -0
  34. data/spec/unit/git/cache_spec.rb +2 -15
  35. data/spec/unit/git/rugged/cache_spec.rb +19 -0
  36. data/spec/unit/module/tarball_spec.rb +70 -0
  37. data/spec/unit/module_loader/puppetfile_spec.rb +4 -1
  38. data/spec/unit/tarball_spec.rb +57 -0
  39. data/spec/unit/util/cacheable_spec.rb +23 -0
  40. data/spec/unit/util/downloader_spec.rb +98 -0
  41. metadata +29 -16
@@ -0,0 +1,183 @@
1
+ require 'fileutils'
2
+ require 'find'
3
+ require 'minitar'
4
+ require 'tempfile'
5
+ require 'uri'
6
+ require 'zlib'
7
+ require 'r10k/settings'
8
+ require 'r10k/settings/mixin'
9
+ require 'r10k/util/platform'
10
+ require 'r10k/util/cacheable'
11
+ require 'r10k/util/downloader'
12
+
13
+ module R10K
14
+ class Tarball
15
+
16
+ include R10K::Settings::Mixin
17
+ include R10K::Util::Cacheable
18
+ include R10K::Util::Downloader
19
+
20
+ def_setting_attr :proxy # Defaults to global proxy setting
21
+ def_setting_attr :cache_root, R10K::Util::Cacheable.default_cachedir
22
+
23
+ # @!attribute [rw] name
24
+ # @return [String] The tarball's name
25
+ attr_accessor :name
26
+
27
+ # @!attribute [rw] source
28
+ # @return [String] The tarball's source
29
+ attr_accessor :source
30
+
31
+ # @!attribute [rw] checksum
32
+ # @return [String] The tarball's expected sha256 digest
33
+ attr_accessor :checksum
34
+
35
+ # @param name [String] The name of the tarball content
36
+ # @param source [String] The source for the tarball content
37
+ # @param checksum [String] The sha256 digest of the tarball content
38
+ def initialize(name, source, checksum: nil)
39
+ @name = name
40
+ @source = source
41
+ @checksum = checksum
42
+
43
+ # At this time, the only checksum type supported is sha256. In the future,
44
+ # we may decide to support other algorithms if a use case arises. TBD.
45
+ checksum_algorithm = :SHA256
46
+ end
47
+
48
+ # @return [String] Directory. Where the cache_basename file will be created.
49
+ def cache_dirname
50
+ File.join(settings[:cache_root], 'tarball')
51
+ end
52
+
53
+ # The final cache_path should match one of the templates:
54
+ #
55
+ # - {cachedir}/{checksum}.tar.gz
56
+ # - {cachedir}/{source}.tar.gz
57
+ #
58
+ # @return [String] File. The full file path the tarball will be cached to.
59
+ def cache_path
60
+ File.join(cache_dirname, cache_basename)
61
+ end
62
+
63
+ # @return [String] The basename of the tarball cache file.
64
+ def cache_basename
65
+ if checksum.nil?
66
+ sanitized_dirname(source) + '.tar.gz'
67
+ else
68
+ checksum + '.tar.gz'
69
+ end
70
+ end
71
+
72
+ # Extract the cached tarball to the target directory.
73
+ #
74
+ # @param target_dir [String] Where to unpack the tarball
75
+ def unpack(target_dir)
76
+ file = File.open(cache_path, 'rb')
77
+ reader = Zlib::GzipReader.new(file)
78
+ begin
79
+ Minitar.unpack(reader, target_dir)
80
+ ensure
81
+ reader.close
82
+ end
83
+ end
84
+
85
+ # @param target_dir [String] The directory to check if is in sync with the
86
+ # tarball content
87
+ # @param ignore_untracked_files [Boolean] If true, consider the target
88
+ # dir to be in sync as long as all tracked content matches.
89
+ #
90
+ # @return [Boolean]
91
+ def insync?(target_dir, ignore_untracked_files: false)
92
+ target_tree_entries = Find.find(target_dir).map(&:to_s) - [target_dir]
93
+ each_tarball_entry do |entry|
94
+ found = target_tree_entries.delete(File.join(target_dir, entry.full_name.chomp('/')))
95
+ return false if found.nil?
96
+ next if entry.directory?
97
+ return false unless file_digest(found) == reader_digest(entry)
98
+ end
99
+
100
+ if ignore_untracked_files
101
+ # We wouldn't have gotten this far if there were discrepancies in
102
+ # tracked content
103
+ true
104
+ else
105
+ # If there are still files in target_tree_entries, then there is
106
+ # untracked content present in the target tree. If not, we're in sync.
107
+ target_tree_entries.empty?
108
+ end
109
+ end
110
+
111
+ # Download the tarball from @source to @cache_path
112
+ def get
113
+ Tempfile.open(cache_basename) do |tempfile|
114
+ tempfile.binmode
115
+ src_uri = URI.parse(source)
116
+
117
+ temp_digest = case src_uri.scheme
118
+ when 'file', nil
119
+ copy(src_uri.path, tempfile)
120
+ when %r{^[a-z]$} # Windows drive letter
121
+ copy(src_uri.to_s, tempfile)
122
+ when %r{^https?$}
123
+ download(src_uri, tempfile)
124
+ else
125
+ raise "Unexpected source scheme #{src_uri.scheme}"
126
+ end
127
+
128
+ # Verify the download
129
+ unless (checksum == temp_digest) || checksum.nil?
130
+ raise 'Downloaded file does not match checksum'
131
+ end
132
+
133
+ # Move the download to cache_path
134
+ FileUtils::mkdir_p(cache_dirname)
135
+ begin
136
+ FileUtils.mv(tempfile.path, cache_path)
137
+ rescue Errno::EACCES
138
+ # It may be the case that permissions don't permit moving the file
139
+ # into place, but do permit overwriting an existing in-place file.
140
+ FileUtils.cp(tempfile.path, cache_path)
141
+ end
142
+ end
143
+ end
144
+
145
+ # Checks the cached tarball's digest against the expected checksum. Returns
146
+ # false if no cached file is present. If the tarball has no expected
147
+ # checksum, any cached file is assumed to be valid.
148
+ #
149
+ # @return [Boolean]
150
+ def cache_valid?
151
+ return false unless File.exist?(cache_path)
152
+ return true if checksum.nil?
153
+ checksum == file_digest(cache_path)
154
+ end
155
+
156
+ # List all of the files contained in the tarball and their paths. This is
157
+ # useful for implementing R10K::Purgable
158
+ #
159
+ # @return [Array] A normalized list of file paths contained in the archive
160
+ def paths
161
+ names = Array.new
162
+ each_tarball_entry { |entry| names << Pathname.new(entry).cleanpath.to_s }
163
+ names - ['.']
164
+ end
165
+
166
+ def cache_checksum
167
+ raise R10K::Error, _("Cache not present at %{path}") % {path: cache_path} unless File.exist?(cache_path)
168
+ file_digest(cache_path)
169
+ end
170
+
171
+ private
172
+
173
+ def each_tarball_entry(&block)
174
+ File.open(cache_path, 'rb') do |file|
175
+ Zlib::GzipReader.wrap(file) do |reader|
176
+ Archive::Tar::Minitar::Input.each_entry(reader) do |entry|
177
+ yield entry
178
+ end
179
+ end
180
+ end
181
+ end
182
+ end
183
+ end
@@ -0,0 +1,31 @@
1
+ module R10K
2
+ module Util
3
+
4
+ # Utility mixin for classes that need to implement caches
5
+ #
6
+ # @abstract Classes using this mixin need to implement {#managed_directory} and
7
+ # {#desired_contents}
8
+ module Cacheable
9
+
10
+ # Provide a default cachedir location. This is consumed by R10K::Settings
11
+ # for appropriate global default values.
12
+ #
13
+ # @return [String] Path to the default cache directory
14
+ def self.default_cachedir(basename = 'cache')
15
+ if R10K::Util::Platform.windows?
16
+ File.join(ENV['LOCALAPPDATA'], 'r10k', basename)
17
+ else
18
+ File.join(ENV['HOME'] || '/root', '.r10k', basename)
19
+ end
20
+ end
21
+
22
+ # Reformat a string into something that can be used as a directory
23
+ #
24
+ # @param string [String] An identifier to create a sanitized dirname for
25
+ # @return [String] A sanitized dirname for the given string
26
+ def sanitized_dirname(string)
27
+ string.gsub(/(\w+:\/\/)(.*)(@)/, '\1').gsub(/[^@\w\.-]/, '-')
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,134 @@
1
+ require 'digest'
2
+ require 'net/http'
3
+
4
+ module R10K
5
+ module Util
6
+
7
+ # Utility mixin for classes that need to download files
8
+ module Downloader
9
+
10
+ # Downloader objects need to checksum downloaded or saved content. The
11
+ # algorithm used to perform this checksumming (and therefore the kinds of
12
+ # checksums returned by various methods) is reported by this method.
13
+ #
14
+ # @return [Symbol] The checksum algorithm the downloader uses
15
+ def checksum_algorithm
16
+ @checksum_algorithm ||= :SHA256
17
+ end
18
+
19
+ private
20
+
21
+ # Set the checksum algorithm the downloader should use. It should be a
22
+ # symbol, and a valid Ruby 'digest' library algorithm. The default is
23
+ # :SHA256.
24
+ #
25
+ # @param algorithm [Symbol] The checksum algorithm the downloader should use
26
+ def checksum_algorithm=(algorithm)
27
+ @checksum_algorithm = algorithm
28
+ end
29
+
30
+ CHUNK_SIZE = 64 * 1024 # 64 kb
31
+
32
+ # @param src_uri [URI] The URI to download from
33
+ # @param dst_file [String] The file or path to save to
34
+ # @return [String] The downloaded file's hex digest
35
+ def download(src_uri, dst_file)
36
+ digest = Digest(checksum_algorithm).new
37
+ http_get(src_uri) do |resp|
38
+ File.open(dst_file, 'wb') do |output_stream|
39
+ resp.read_body do |chunk|
40
+ output_stream.write(chunk)
41
+ digest.update(chunk)
42
+ end
43
+ end
44
+ end
45
+
46
+ digest.hexdigest
47
+ end
48
+
49
+ # @param src_file The file or path to copy from
50
+ # @param dst_file The file or path to copy to
51
+ # @return [String] The copied file's sha256 hex digest
52
+ def copy(src_file, dst_file)
53
+ digest = Digest(checksum_algorithm).new
54
+ File.open(src_file, 'rb') do |input_stream|
55
+ File.open(dst_file, 'wb') do |output_stream|
56
+ until input_stream.eof?
57
+ chunk = input_stream.read(CHUNK_SIZE)
58
+ output_stream.write(chunk)
59
+ digest.update(chunk)
60
+ end
61
+ end
62
+ end
63
+
64
+ digest.hexdigest
65
+ end
66
+
67
+ # Start a Net::HTTP::Get connection, then yield the Net::HTTPSuccess object
68
+ # to the caller's block. Follow redirects if Net::HTTPRedirection responses
69
+ # are encountered, and use a proxy if directed.
70
+ #
71
+ # @param uri [URI] The URI to download the file from
72
+ # @param redirect_limit [Integer] How many redirects to permit before failing
73
+ # @param proxy [URI, String] The URI to use as a proxy
74
+ def http_get(uri, redirect_limit: 10, proxy: nil, &block)
75
+ raise "HTTP redirect too deep" if redirect_limit.zero?
76
+
77
+ session = Net::HTTP.new(uri.host, uri.port, *proxy_to_array(proxy))
78
+ session.use_ssl = true if uri.scheme == 'https'
79
+ session.start
80
+
81
+ begin
82
+ session.request_get(uri) do |response|
83
+ case response
84
+ when Net::HTTPRedirection
85
+ redirect = response['location']
86
+ session.finish
87
+ return http_get(URI.parse(redirect), redirect_limit: redirect_limit - 1, proxy: proxy, &block)
88
+ when Net::HTTPSuccess
89
+ yield response
90
+ else
91
+ raise "Unexpected response code #{response.code}: #{response}"
92
+ end
93
+ end
94
+ ensure
95
+ session.finish if session.active?
96
+ end
97
+ end
98
+
99
+ # Helper method to translate a proxy URI to array arguments for
100
+ # Net::HTTP#new. A nil argument returns nil array elements.
101
+ def proxy_to_array(proxy_uri)
102
+ if proxy_uri
103
+ px = proxy_uri.is_a?(URI) ? proxy_uri : URI.parse(proxy_uri)
104
+ [px.host, px.port, px.user, px.password]
105
+ else
106
+ [nil, nil, nil, nil]
107
+ end
108
+ end
109
+
110
+ # Return the sha256 digest of the file at the given path
111
+ #
112
+ # @param path [String] The path to the file
113
+ # @return [String] The file's sha256 hex digest
114
+ def file_digest(path)
115
+ File.open(path) do |file|
116
+ reader_digest(file)
117
+ end
118
+ end
119
+
120
+ # Return the sha256 digest of the readable data
121
+ #
122
+ # @param reader [String] An object that responds to #read
123
+ # @return [String] The read data's sha256 hex digest
124
+ def reader_digest(reader)
125
+ digest = Digest(checksum_algorithm).new
126
+ while chunk = reader.read(CHUNK_SIZE)
127
+ digest.update(chunk)
128
+ end
129
+
130
+ digest.hexdigest
131
+ end
132
+ end
133
+ end
134
+ end
data/lib/r10k/version.rb CHANGED
@@ -2,5 +2,5 @@ module R10K
2
2
  # When updating to a new major (X) or minor (Y) version, include `#major` or
3
3
  # `#minor` (respectively) in your commit message to trigger the appropriate
4
4
  # release. Otherwise, a new patch (Z) version will be released.
5
- VERSION = '3.13.0'
5
+ VERSION = '3.14.0'
6
6
  end
data/locales/r10k.pot CHANGED
@@ -6,11 +6,11 @@
6
6
  #, fuzzy
7
7
  msgid ""
8
8
  msgstr ""
9
- "Project-Id-Version: r10k 3.9.3-134-g9f93336f\n"
9
+ "Project-Id-Version: r10k 3.9.3-170-g8cb36435\n"
10
10
  "\n"
11
11
  "Report-Msgid-Bugs-To: docs@puppetlabs.com\n"
12
- "POT-Creation-Date: 2021-10-25 18:18+0000\n"
13
- "PO-Revision-Date: 2021-10-25 18:18+0000\n"
12
+ "POT-Creation-Date: 2021-11-16 21:43+0000\n"
13
+ "PO-Revision-Date: 2021-11-16 21:43+0000\n"
14
14
  "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
15
15
  "Language-Team: LANGUAGE <LL@li.org>\n"
16
16
  "Language: \n"
@@ -75,15 +75,15 @@ msgstr ""
75
75
  msgid "Syntax OK"
76
76
  msgstr ""
77
77
 
78
- #: ../lib/r10k/action/runner.rb:57 ../lib/r10k/deployment/config.rb:42
78
+ #: ../lib/r10k/action/runner.rb:63 ../lib/r10k/deployment/config.rb:42
79
79
  msgid "Overriding config file setting '%{key}': '%{old_val}' -> '%{new_val}'"
80
80
  msgstr ""
81
81
 
82
- #: ../lib/r10k/action/runner.rb:99
82
+ #: ../lib/r10k/action/runner.rb:105
83
83
  msgid "Reading configuration from %{config_path}"
84
84
  msgstr ""
85
85
 
86
- #: ../lib/r10k/action/runner.rb:102
86
+ #: ../lib/r10k/action/runner.rb:108
87
87
  msgid "No config file explicitly given and no default config file could be found, default settings will be used."
88
88
  msgstr ""
89
89
 
@@ -155,19 +155,19 @@ msgstr ""
155
155
  msgid "Proc %{block} for feature %{name} returned %{output}"
156
156
  msgstr ""
157
157
 
158
- #: ../lib/r10k/forge/module_release.rb:196
158
+ #: ../lib/r10k/forge/module_release.rb:197
159
159
  msgid "Unpacking %{tarball_cache_path} to %{target_dir} (with tmpdir %{tmp_path})"
160
160
  msgstr ""
161
161
 
162
- #: ../lib/r10k/forge/module_release.rb:198
162
+ #: ../lib/r10k/forge/module_release.rb:199
163
163
  msgid "Valid files unpacked: %{valid_files}"
164
164
  msgstr ""
165
165
 
166
- #: ../lib/r10k/forge/module_release.rb:200
166
+ #: ../lib/r10k/forge/module_release.rb:201
167
167
  msgid "These files existed in the module's tar file, but are invalid filetypes and were not unpacked: %{invalid_files}"
168
168
  msgstr ""
169
169
 
170
- #: ../lib/r10k/forge/module_release.rb:203
170
+ #: ../lib/r10k/forge/module_release.rb:204
171
171
  msgid "Symlinks are unsupported and were not unpacked from the module tarball. %{release_slug} contained these ignored symlinks: %{symlinks}"
172
172
  msgstr ""
173
173
 
@@ -203,11 +203,11 @@ msgstr ""
203
203
  msgid "Cannot write %{file}; parent directory does not exist"
204
204
  msgstr ""
205
205
 
206
- #: ../lib/r10k/git/cache.rb:65
206
+ #: ../lib/r10k/git/cache.rb:57
207
207
  msgid "%{class}#path is deprecated; use #git_dir"
208
208
  msgstr ""
209
209
 
210
- #: ../lib/r10k/git/cache.rb:94
210
+ #: ../lib/r10k/git/cache.rb:86
211
211
  msgid "Creating new git cache for %{remote}"
212
212
  msgstr ""
213
213
 
@@ -223,6 +223,14 @@ msgstr ""
223
223
  msgid "Rugged versions prior to 0.24.0 do not support pruning stale branches during fetch, please upgrade your \\'rugged\\' gem. (Current version is: %{version})"
224
224
  msgstr ""
225
225
 
226
+ #: ../lib/r10k/git/rugged/base_repository.rb:24
227
+ msgid "Unable to resolve %{pattern}: %{e} "
228
+ msgstr ""
229
+
230
+ #: ../lib/r10k/git/rugged/base_repository.rb:69
231
+ msgid "Remote URL is different from cache, updating %{orig} to %{update}"
232
+ msgstr ""
233
+
226
234
  #: ../lib/r10k/git/rugged/credentials.rb:28
227
235
  msgid "Authentication failed for Git remote %{url}."
228
236
  msgstr ""
@@ -367,7 +375,7 @@ msgstr ""
367
375
  msgid "%{repo_path} is already at Git ref %{ref}"
368
376
  msgstr ""
369
377
 
370
- #: ../lib/r10k/initializers.rb:30
378
+ #: ../lib/r10k/initializers.rb:31
371
379
  msgid "the purgedirs key in r10k.yaml is deprecated. it is currently ignored."
372
380
  msgstr ""
373
381
 
@@ -379,7 +387,7 @@ msgstr ""
379
387
  msgid "No class registered for %{key}"
380
388
  msgstr ""
381
389
 
382
- #: ../lib/r10k/logging.rb:60
390
+ #: ../lib/r10k/logging.rb:73 ../lib/r10k/logging.rb:100 ../lib/r10k/logging.rb:109
383
391
  msgid "Invalid log level '%{val}'. Valid levels are %{log_levels}"
384
392
  msgstr ""
385
393
 
@@ -439,39 +447,43 @@ msgstr ""
439
447
  msgid "Could not read metadata.json"
440
448
  msgstr ""
441
449
 
442
- #: ../lib/r10k/module_loader/puppetfile.rb:62
450
+ #: ../lib/r10k/module_loader/puppetfile.rb:64
443
451
  msgid "Using Puppetfile '%{puppetfile}'"
444
452
  msgstr ""
445
453
 
446
- #: ../lib/r10k/module_loader/puppetfile.rb:63
454
+ #: ../lib/r10k/module_loader/puppetfile.rb:65
447
455
  msgid "Using moduledir '%{moduledir}'"
448
456
  msgstr ""
449
457
 
450
- #: ../lib/r10k/module_loader/puppetfile.rb:84
458
+ #: ../lib/r10k/module_loader/puppetfile.rb:86
451
459
  msgid "Failed to evaluate %{path}"
452
460
  msgstr ""
453
461
 
454
- #: ../lib/r10k/module_loader/puppetfile.rb:101
462
+ #: ../lib/r10k/module_loader/puppetfile.rb:103
455
463
  msgid "Unable to preload Puppetfile because of %{msg}"
456
464
  msgstr ""
457
465
 
458
- #: ../lib/r10k/module_loader/puppetfile.rb:119
466
+ #: ../lib/r10k/module_loader/puppetfile.rb:121
459
467
  msgid "Using Forge from Puppetfile: %{forge}"
460
468
  msgstr ""
461
469
 
462
- #: ../lib/r10k/module_loader/puppetfile.rb:122
470
+ #: ../lib/r10k/module_loader/puppetfile.rb:124
463
471
  msgid "Ignoring Forge declaration in Puppetfile, using value from settings: %{forge}."
464
472
  msgstr ""
465
473
 
466
- #: ../lib/r10k/module_loader/puppetfile.rb:183 ../lib/r10k/puppetfile.rb:104
474
+ #: ../lib/r10k/module_loader/puppetfile.rb:173
475
+ msgid "\"basedir\" is deprecated. Please use \"environment_name\" instead. \"basedir\" will be removed in a future version."
476
+ msgstr ""
477
+
478
+ #: ../lib/r10k/module_loader/puppetfile.rb:192 ../lib/r10k/puppetfile.rb:104
467
479
  msgid "Puppetfile %{path} missing or unreadable"
468
480
  msgstr ""
469
481
 
470
- #: ../lib/r10k/module_loader/puppetfile.rb:219
482
+ #: ../lib/r10k/module_loader/puppetfile.rb:228
471
483
  msgid "Puppetfiles cannot contain duplicate module names."
472
484
  msgstr ""
473
485
 
474
- #: ../lib/r10k/module_loader/puppetfile.rb:221
486
+ #: ../lib/r10k/module_loader/puppetfile.rb:230
475
487
  msgid "Remove the duplicates of the following modules: %{dupes}"
476
488
  msgstr ""
477
489
 
@@ -602,6 +614,10 @@ msgstr ""
602
614
  msgid "Both username and password must be specified"
603
615
  msgstr ""
604
616
 
617
+ #: ../lib/r10k/tarball.rb:167
618
+ msgid "Cache not present at %{path}"
619
+ msgstr ""
620
+
605
621
  #: ../lib/r10k/util/basedir.rb:34
606
622
  msgid "Expected Array<#desired_contents>, got R10K::Deployment"
607
623
  msgstr ""
data/r10k.gemspec CHANGED
@@ -32,18 +32,18 @@ Gem::Specification.new do |s|
32
32
 
33
33
  s.add_dependency 'gettext-setup', '~>0.24'
34
34
  # These two pins narrow what is allowed by gettext-setup,
35
- # to preserver compatability with Ruby 2.4
35
+ # to preserve compatability with Ruby 2.4
36
36
  s.add_dependency 'fast_gettext', '~> 1.1.0'
37
37
  s.add_dependency 'gettext', ['>= 3.0.2', '< 3.3.0']
38
38
 
39
39
  s.add_dependency 'jwt', '~> 2.2.3'
40
+ s.add_dependency 'minitar', '~> 0.9.0'
40
41
 
41
42
  s.add_development_dependency 'rspec', '~> 3.1'
42
43
 
43
44
  s.add_development_dependency 'rake'
44
45
 
45
46
  s.add_development_dependency 'yard', '~> 0.9.11'
46
- s.add_development_dependency 'minitar', '~> 0.9.0'
47
47
 
48
48
  s.files = %x[git ls-files].split($/)
49
49
  s.require_path = 'lib'
@@ -0,0 +1,33 @@
1
+ require 'spec_helper'
2
+ require 'r10k/git/rugged/cache'
3
+
4
+ describe R10K::Git::Rugged::Cache, :if => R10K::Features.available?(:rugged) do
5
+ include_context 'Git integration'
6
+
7
+ let(:dirname) { 'working-repo' }
8
+ let(:remote_name) { 'origin' }
9
+
10
+ subject { described_class.new(remote) }
11
+
12
+ context "syncing with the remote" do
13
+ before(:each) do
14
+ subject.reset!
15
+ end
16
+
17
+ describe "with the correct configuration" do
18
+ it "is able to sync with the remote" do
19
+ subject.sync
20
+ expect(subject.synced?).to eq(true)
21
+ end
22
+ end
23
+
24
+ describe "with a out of date cached remote" do
25
+ it "updates the cached remote configuration" do
26
+ subject.repo.update_remote('foo', remote_name)
27
+ expect(subject.repo.remotes[remote_name]).to eq('foo')
28
+ subject.sync
29
+ expect(subject.repo.remotes[remote_name]).to eq(remote)
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,32 @@
1
+ require 'tmpdir'
2
+ require 'fileutils'
3
+
4
+ shared_context "Tarball" do
5
+ # Suggested subject:
6
+ #
7
+ # subject { described_class.new('fixture-tarball', fixture_tarball, checksum: fixture_checksum) }
8
+ #
9
+ let(:fixture_tarball) do
10
+ File.expand_path('spec/fixtures/tarball/tarball.tar.gz', PROJECT_ROOT)
11
+ end
12
+
13
+ let(:fixture_checksum) { '292e692ad18faabd4f9b21037d51f0185e04b69f82c522a54af91fb5b88c2d3b' }
14
+
15
+ # Use tmpdir for cached tarballs
16
+ let(:tmpdir) { Dir.mktmpdir }
17
+
18
+ # `moduledir` and `cache_root` are available for examples to use in creating
19
+ # their subjects
20
+ let(:moduledir) { File.join(tmpdir, 'modules').tap { |path| Dir.mkdir(path) } }
21
+ let(:cache_root) { File.join(tmpdir, 'cache').tap { |path| Dir.mkdir(path) } }
22
+
23
+ around(:each) do |example|
24
+ if subject.is_a?(R10K::Tarball)
25
+ subject.settings[:cache_root] = cache_root
26
+ elsif subject.respond_to?(:tarball) && subject.tarball.is_a?(R10K::Tarball)
27
+ subject.tarball.settings[:cache_root] = cache_root
28
+ end
29
+ example.run
30
+ FileUtils.remove_entry_secure(tmpdir)
31
+ end
32
+ end
data/spec/spec_helper.rb CHANGED
@@ -19,6 +19,7 @@ require 'r10k'
19
19
  Dir.glob(File.expand_path('spec/shared-examples/**/*.rb', PROJECT_ROOT)).each { |file| require file }
20
20
 
21
21
  require 'shared-contexts/git-fixtures'
22
+ require 'shared-contexts/tarball'
22
23
  require 'matchers/exit_with'
23
24
  require 'matchers/match_realpath'
24
25
  require 'r10k-mocks'
@@ -241,7 +241,7 @@ describe R10K::Action::Deploy::Module do
241
241
 
242
242
  allow(R10K::Git::StatefulRepository).to receive(:new).and_return(repo)
243
243
  allow(R10K::Git).to receive_message_chain(:cache, :generate).and_return(cache)
244
- allow_any_instance_of(R10K::Source::Git).to receive(:branch_names).and_return([R10K::Environment::Name.new('first', {})])
244
+ allow_any_instance_of(R10K::Source::Git).to receive(:environment_names).and_return([R10K::Environment::Name.new('first', {})])
245
245
 
246
246
  expect(subject).to receive(:visit_environment).and_wrap_original do |original, environment, &block|
247
247
  # For this test we want to have realistic Modules and access to
@@ -300,7 +300,7 @@ describe R10K::Action::Deploy::Module do
300
300
 
301
301
  allow(R10K::Git::StatefulRepository).to receive(:new).and_return(repo)
302
302
  allow(R10K::Git).to receive_message_chain(:cache, :generate).and_return(cache)
303
- allow_any_instance_of(R10K::Source::Git).to receive(:branch_names).and_return([R10K::Environment::Name.new('first', {}),
303
+ allow_any_instance_of(R10K::Source::Git).to receive(:environment_names).and_return([R10K::Environment::Name.new('first', {}),
304
304
  R10K::Environment::Name.new('second', {})])
305
305
 
306
306
  expect(subject).to receive(:visit_environment).and_wrap_original do |original, environment, &block|