docker-api 0.0.5 → 0.0.6

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.
data/README.md CHANGED
@@ -131,9 +131,13 @@ Docker::Image.all
131
131
  Docker::Image.search('term' => 'sshd')
132
132
  # => [Docker::Image { :id => cespare/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => johnfuller/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => dhrp/mongodb-sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => rayang2004/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => dhrp/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => toorop/daemontools-sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => toorop/daemontools-sshd-nginx, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => toorop/daemontools-sshd-nginx-php-fpm, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => mbkan/lamp, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => toorop/golang, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => wma55/u1210sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => jdswinbank/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }, Docker::Image { :id => vgauthier/sshd, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }]
133
133
 
134
- # Create an Image from a Dockerfile.
134
+ # Create an Image from a Dockerfile as a String.
135
135
  Docker::Image.build("from base\nrun touch /test")
136
136
  # => Docker::Image { :id => b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }
137
+
138
+ # Create an Image from a Dockerfile.
139
+ Dockerfile::Image.build_from_file(File.new('Dockerfile'))
140
+ # => Docker::Image { :id => 1266dc19e, :connection => Docker::Connection { :url => http://localhost, :options => {:port=>4243} } }
137
141
  ```
138
142
 
139
143
  ## Containers
data/docker-api.gemspec CHANGED
@@ -18,6 +18,7 @@ Gem::Specification.new do |gem|
18
18
  gem.add_dependency 'json'
19
19
  gem.add_dependency 'i18n'
20
20
  gem.add_dependency 'multipart-post'
21
+ gem.add_dependency 'archive-tar-minitar'
21
22
  gem.add_development_dependency 'rake'
22
23
  gem.add_development_dependency 'rspec'
23
24
  gem.add_development_dependency 'cane'
data/lib/docker.rb CHANGED
@@ -1,6 +1,9 @@
1
1
  require 'cgi'
2
2
  require 'json'
3
+ require 'zlib'
3
4
  require 'excon'
5
+ require 'tempfile'
6
+ require 'archive/tar/minitar'
4
7
  require 'net/http/post/multipart'
5
8
 
6
9
  # The top-level module for this gem. It's purpose is to hold global
data/lib/docker/image.rb CHANGED
@@ -86,12 +86,34 @@ class Docker::Image
86
86
 
87
87
  # Given a Dockerfile as a string, builds an Image.
88
88
  def build(commands, connection = Docker.connection)
89
- body = multipart_request(
89
+ req = build_multipart_post('/build', :io => StringIO.new("#{commands}\n"),
90
+ :name => 'Dockerfile',
91
+ :file_name => 'Dockerfile',
92
+ :content_type => 'text/plain')
93
+ body = multipart_request(connection, req)
94
+ new(:id => extract_id(body), :connection => connection)
95
+ end
96
+
97
+ def build_from_file(file, connection = Docker.connection)
98
+ path = File.dirname(File.absolute_path(file.to_path))
99
+ context_io = create_tar_gz(path)
100
+ req = build_multipart_post(
90
101
  '/build',
91
- 'Dockerfile',
92
- StringIO.new("#{commands}\n"),
93
- connection
102
+ {
103
+ :io => file,
104
+ :name => 'Dockerfile',
105
+ :file_name => 'Dockerfile',
106
+ :content_type => 'text/plain'
107
+ },
108
+ {
109
+ :io => context_io,
110
+ :name => 'Context',
111
+ :file_name => 'dir.tar.gz',
112
+ :content_type => 'application/octet-stream'
113
+ }
94
114
  )
115
+ body = multipart_request(connection, req)
116
+ context_io.close
95
117
  new(:id => extract_id(body), :connection => connection)
96
118
  end
97
119
 
@@ -103,5 +125,12 @@ class Docker::Image
103
125
  raise UnexpectedResponseError, "Couldn't find id: #{body}"
104
126
  end
105
127
  end
128
+
129
+ def create_tar_gz(directory)
130
+ tempfile = Tempfile.new('output')
131
+ zlb = Zlib::GzipWriter.new(tempfile)
132
+ Archive::Tar::Minitar.pack(directory, zlb)
133
+ File.new(tempfile.path, 'r')
134
+ end
106
135
  end
107
136
  end
@@ -3,12 +3,9 @@ module Docker::Multipart
3
3
  include Docker::Error
4
4
 
5
5
  # Given a path, resource name, io, and Connection sends a multipart request.
6
- def multipart_request(path, name, io, connection)
6
+ def multipart_request(connection, request)
7
7
  host, port = host_and_port(connection)
8
- res = Net::HTTP.start(host, port) { |http|
9
- req = build_multipart_post(path, io, 'application/octet-stream', name)
10
- http.request(req)
11
- }
8
+ res = Net::HTTP.start(host, port) { |http| http.request(request) }
12
9
  if (200..204).include?(res.code.to_i)
13
10
  res.body
14
11
  else
@@ -16,15 +13,19 @@ module Docker::Multipart
16
13
  end
17
14
  end
18
15
 
16
+ def build_multipart_post(path, *io_opts_list)
17
+ options = Hash[io_opts_list.map { |opts|
18
+ [
19
+ opts[:name],
20
+ UploadIO.new(opts[:io], opts[:content_type], opts[:file_name])
21
+ ]
22
+ }]
23
+ Net::HTTP::Post::Multipart.new(path, options)
24
+ end
25
+
19
26
  private
20
27
  # Return the host and port from a Connection.
21
28
  def host_and_port(connection)
22
29
  [URI.parse(connection.url).host, connection.options[:port]]
23
30
  end
24
-
25
- # Build the multipart post request.
26
- def build_multipart_post(path, inner_io, content_type, file_name)
27
- io = UploadIO.new(inner_io, content_type, file_name)
28
- Net::HTTP::Post::Multipart.new(path, file_name => io)
29
- end
30
31
  end
@@ -1,3 +1,3 @@
1
1
  module Docker
2
- VERSION = "0.0.5"
2
+ VERSION = "0.0.6"
3
3
  end
@@ -409,14 +409,36 @@ describe Docker::Image do
409
409
  end
410
410
  end
411
411
 
412
- context 'with a valid Dockerfile', :vcr do
412
+ context 'with a valid Dockerfile' do
413
413
  let(:image) { subject.build("from base\n") }
414
414
 
415
- it 'builds an image' do
415
+ it 'builds an image', :vcr do
416
416
  image.should be_a Docker::Image
417
417
  image.id.should_not be_nil
418
418
  image.connection.should be_a Docker::Connection
419
419
  end
420
420
  end
421
421
  end
422
+
423
+ describe '.build_from_file' do
424
+ subject { described_class }
425
+
426
+ context 'with a valid Dockerfile' do
427
+ let(:file_name) do
428
+ File.join(File.dirname(__FILE__), '..', 'fixtures', 'Dockerfile')
429
+ end
430
+ let(:docker_file) { File.new(file_name) }
431
+ let(:image) { subject.build_from_file(docker_file) }
432
+ let(:container) do
433
+ Docker::Container.new.create!('Image' => image.id,
434
+ 'Cmd' => %w[cat /Dockerfile])
435
+ end
436
+ let(:output) { container.tap(&:start)
437
+ .attach(:stream => true, :stdout => true) }
438
+
439
+ it 'builds the image', :vcr do
440
+ output.should == docker_file.read
441
+ end
442
+ end
443
+ end
422
444
  end
@@ -0,0 +1,2 @@
1
+ from base
2
+ add / Dockerfile
@@ -0,0 +1,179 @@
1
+ ---
2
+ http_interactions:
3
+ - request:
4
+ method: post
5
+ uri: http://localhost:4243/build
6
+ body:
7
+ encoding: ASCII-8BIT
8
+ string: !binary |-
9
+ LS0tLS0tLS0tLS0tLVJ1YnlNdWx0aXBhcnRQb3N0DQpDb250ZW50LURpc3Bv
10
+ c2l0aW9uOiBmb3JtLWRhdGE7IG5hbWU9IkRvY2tlcmZpbGUiOyBmaWxlbmFt
11
+ ZT0iRG9ja2VyZmlsZSINCkNvbnRlbnQtTGVuZ3RoOiAyNw0KQ29udGVudC1U
12
+ eXBlOiB0ZXh0L3BsYWluDQpDb250ZW50LVRyYW5zZmVyLUVuY29kaW5nOiBi
13
+ aW5hcnkNCg0KZnJvbSBiYXNlCmFkZCAvIERvY2tlcmZpbGUKDQotLS0tLS0t
14
+ LS0tLS0tUnVieU11bHRpcGFydFBvc3QNCkNvbnRlbnQtRGlzcG9zaXRpb246
15
+ IGZvcm0tZGF0YTsgbmFtZT0iQ29udGV4dCI7IGZpbGVuYW1lPSJkaXIudGFy
16
+ Lmd6Ig0KQ29udGVudC1MZW5ndGg6IDE3MjENCkNvbnRlbnQtVHlwZTogYXBw
17
+ bGljYXRpb24vb2N0ZXQtc3RyZWFtDQpDb250ZW50LVRyYW5zZmVyLUVuY29k
18
+ aW5nOiBiaW5hcnkNCg0KH4sIANOfxFEAA+3dDVAUVRwA8MWaUQ/xIyEUnWGR
19
+ 9EDgdvfu4OD00DRRVBQcQE2TFm6BlYM77vZAEKUsNBE10zQHyBQlYCIEjRBR
20
+ bAQNP/MrNUEtIPwgJYKID712T84PHAPETsv/b+bNu/14b9/u293ZN7f/WSxU
21
+ GU5hTKhWQYeSEZgmmlZRihhMrgwKo9ROpIrGNCoqCAumFzFaNaVBngaOi3GJ
22
+ xJnNcULijD+cGyCEkHAhCMJZLGLnExKCkCCo81NtrZu0GoZUs00xxrZeQFj3
23
+ +h8TvKVfEkwrKIEmWtWlbeAEjrvg+BP6X/Ro/3PzhUJcJEZQo/TJS97/gbi/
24
+ pxcqEYi4iYEIMiS5xKfClEHOoghiOCs6q4NSkHQE1fm2lnb9NHtwlvV4DwEA
25
+ 95ghIiGhv9XZjrBBB7/m97wbBAAAAAAAADAiRmWCxLN5r/ZpQ27SIQcAAAAA
26
+ AAAAAMB/FylHkO8GIEg1m7j//w3j/z8N8wAAAAAAAAAAAPCCIOVyFEOfGMtx
27
+ b/FD79QHq5XhaCCpobof/8FQGkagDuxy8AfSHv8hFncl/gN3Ibj4D0IklkD8
28
+ hzF0jP9I+rjE5wzvucd/tJ9lPd49AMB9EP8BAAAAAADAy6xj/Idpew7xHwAA
29
+ AAAAAAAAwP8HF/+RbYYgjWzi/v83jP8vD0CQCjYVsknFJgGbavojSDKb3mST
30
+ BZua2ss1mD3PPQAAAAAAAAAA8ERLEBRVaRkNGsowKoGaitRSGsaOze0FgUp5
31
+ DDKDYqTSKb6+3gLu5XjGjq9QBpGKUKWG4TuiYqFYZI8uRuO4wnEIWwqVofdL
32
+ SKXe7GpSqZdWwdAqtrAggoq242OBWlohZ0vzJyojGGoRw0dl7iitZGc8CEvQ
33
+ z1MyoZQ6gFbaI4ZfbPV+KoWSlHvO1FfmwX17Ql/rQ0Xt2Zq4ejEV9zI6/9F6
34
+ 7ZHHa+EWsGuRKpWCDiIZWhmBKYMYinHSMGqKDOdqMLyNLmAPgiAklq3GFu3Z
35
+ 7nI19LwpgbFCti1cKbamB0fj8eZynaOl1RTKj6AYjOsvTMU2Fws3tJbf7fiP
36
+ p/kwgz7+w+VJ8R9cCIjo0e+/CAl2AuI/jOF+JBCvY5AQ73k3DRhBd6//DjeZ
37
+ Lm2jk+ufEOOG6x+XuIgJ7vs/hMQFrn9jsF7VB9m6tsQHeeW3CpnyzPghveu+
38
+ /KisT+K7crdrVz22uRe/kW+e6VgUZbd71tHElKqsOa65uScXmjrd6VU3ck7z
39
+ QEcLB1OHOJOo4FsTyid4D8sq2nBaN1Oa+kn5xbWakGk+t07NTRl1wn/ZF+lh
40
+ /IyLxT+OVM8/HD38Us6erNRK33e2zAmv3zrIYk8/0aEp+atcF66oSPvJrLUt
41
+ Ka9Ai9Hulhc9zE0drkznq/rLDuwPtybuXr5dedttYdu5ur0ltX1L6ldo3O+a
42
+ tV4/LTR1nFlcMHX33ah4beu27Sdrb2NzS8izFgdPNhaORU9K0nxLLhWdS441
43
+ Ja1+H2vhtX9QeNmIwW7jUtbbBtggbczmseevy/xrIirk53Oyt0SN1x8WfJIw
44
+ davML+BaseDm5vet2g/Wia93TmqI2HgtbXSLTlffpGuql7Uv+Wvyh9mvVyZ9
45
+ u37N1cNOefF20n3OjcPmniZX45ZS3cTE+W/PDZpQZs3ktQ04fKrZesHxpnU6
46
+ wuyDZuumK7U5SwuZG83Wd9zc6qtNDphUxesrTAlhl3oUe9ztfW8DB3QTa+LL
47
+ CyY0TLe4o4tvbtXddDxl6eeeMSvjl8x6r29ico58Ppq82L7ye6Gbhkwz3bwr
48
+ f0PmpystE76vLspy8Lelw88E2dxsnBwW5rBxwXKs5rgrvTxyTNmOmGS/iqzZ
49
+ ZM6FNbeKJmZZzpP3lt1otDj31YIAQeDQHVm7zlkk/zFKae5TPmvf8b2esxOd
50
+ 6LzSMY5TR5uPzGqNteKTYdc9c3JPJHibHRSvTgu2S9t+dH26udpm0+Y+Y1rQ
51
+ 6kRmWkKI84LC4IRfL2SsO5YbWbptcaat7Ifk6IYZsQWRy1p846lJG/oGRyVU
52
+ tcyrykzcEH1kvFde+s6z+zfpfp69tlxXmiNd0Wydf1lXalZuVT8unbzWj0gK
53
+ qvmMyN+jSIoLGFqZKD/rOqPOV7RmibvV3kN1NsNXOidk+y+v0EVd7V+rq/JL
54
+ RZp04uHyXlb8YzYpDSWv6o9QbqvJFKuAFmSRka6zF1V37/9PE5jZ2f0fJ+4/
55
+ /7GPfux6Qlzs4gz3f2PodITA43U+0OA9s1ENr8cjLN6zGerxnuHok/evjZF5
56
+ 3Rip8/5xzM9bAs/7AADwMvkbF0sKYAB6AAANCi0tLS0tLS0tLS0tLS1SdWJ5
57
+ TXVsdGlwYXJ0UG9zdC0tDQoNCg==
58
+ headers:
59
+ Accept:
60
+ - ! '*/*'
61
+ User-Agent:
62
+ - Ruby
63
+ Content-Type:
64
+ - multipart/form-data; boundary=-----------RubyMultipartPost
65
+ Content-Length:
66
+ - '2179'
67
+ response:
68
+ status:
69
+ code: 200
70
+ message: OK
71
+ headers:
72
+ Content-Type:
73
+ - text/plain; charset=utf-8
74
+ Date:
75
+ - Fri, 21 Jun 2013 18:47:47 GMT
76
+ Transfer-Encoding:
77
+ - chunked
78
+ body:
79
+ encoding: US-ASCII
80
+ string: ! 'FROM base ()
81
+
82
+ ===> b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc
83
+
84
+ ADD / Dockerfile (b750fe79269d2ec9a3c593ef05b4332b1d1a02a62b4accb2c21d589ff2f5f2dc)
85
+
86
+ ===> e495b94e01c093c92998c1d181fcedf53e3ff6d40887b640f9ea14600bd69a06
87
+
88
+ Build successful.
89
+
90
+ ===> e495b94e01c093c92998c1d181fcedf53e3ff6d40887b640f9ea14600bd69a06
91
+
92
+ '
93
+ http_version:
94
+ recorded_at: Fri, 21 Jun 2013 18:47:47 GMT
95
+ - request:
96
+ method: post
97
+ uri: http://localhost:4243/containers/create
98
+ body:
99
+ encoding: UTF-8
100
+ string: ! '{"Image":"e495b94e01c093c92998c1d181fcedf53e3ff6d40887b640f9ea14600bd69a06","Cmd":["cat","/Dockerfile"]}'
101
+ headers:
102
+ Content-Type:
103
+ - text/plain
104
+ User-Agent:
105
+ - Docker-Client/1.2
106
+ response:
107
+ status:
108
+ code: 201
109
+ message: ''
110
+ headers:
111
+ !binary "Q29udGVudC1UeXBl":
112
+ - !binary |-
113
+ dGV4dC9wbGFpbjsgY2hhcnNldD11dGYtOA==
114
+ !binary "Q29udGVudC1MZW5ndGg=":
115
+ - !binary |-
116
+ MjE=
117
+ !binary "RGF0ZQ==":
118
+ - !binary |-
119
+ RnJpLCAyMSBKdW4gMjAxMyAxODo0Nzo0NyBHTVQ=
120
+ body:
121
+ encoding: US-ASCII
122
+ string: ! '{"Id":"4fce10ce5469"}'
123
+ http_version:
124
+ recorded_at: Fri, 21 Jun 2013 18:47:47 GMT
125
+ - request:
126
+ method: post
127
+ uri: http://localhost:4243/containers/4fce10ce5469/start
128
+ body:
129
+ encoding: US-ASCII
130
+ string: ''
131
+ headers:
132
+ Content-Type:
133
+ - text/plain
134
+ User-Agent:
135
+ - Docker-Client/1.2
136
+ response:
137
+ status:
138
+ code: 204
139
+ message: ''
140
+ headers:
141
+ !binary "Q29udGVudC1UeXBl":
142
+ - !binary |-
143
+ dGV4dC9wbGFpbjsgY2hhcnNldD11dGYtOA==
144
+ !binary "Q29udGVudC1MZW5ndGg=":
145
+ - !binary |-
146
+ MA==
147
+ !binary "RGF0ZQ==":
148
+ - !binary |-
149
+ RnJpLCAyMSBKdW4gMjAxMyAxODo0Nzo0NyBHTVQ=
150
+ body:
151
+ encoding: US-ASCII
152
+ string: ''
153
+ http_version:
154
+ recorded_at: Fri, 21 Jun 2013 18:47:47 GMT
155
+ - request:
156
+ method: post
157
+ uri: http://localhost:4243/containers/4fce10ce5469/attach?stdout=true&stream=true
158
+ body:
159
+ encoding: US-ASCII
160
+ string: ''
161
+ headers:
162
+ Content-Type:
163
+ - text/plain
164
+ User-Agent:
165
+ - Docker-Client/1.2
166
+ response:
167
+ status:
168
+ code: 200
169
+ message: ''
170
+ headers:
171
+ !binary "Q29udGVudC1UeXBl":
172
+ - !binary |-
173
+ YXBwbGljYXRpb24vdm5kLmRvY2tlci5yYXctc3RyZWFt
174
+ body:
175
+ encoding: US-ASCII
176
+ string: ''
177
+ http_version:
178
+ recorded_at: Fri, 21 Jun 2013 18:47:48 GMT
179
+ recorded_with: VCR 2.5.0
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: docker-api
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 0.0.6
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -75,6 +75,22 @@ dependencies:
75
75
  - - ! '>='
76
76
  - !ruby/object:Gem::Version
77
77
  version: '0'
78
+ - !ruby/object:Gem::Dependency
79
+ name: archive-tar-minitar
80
+ requirement: !ruby/object:Gem::Requirement
81
+ none: false
82
+ requirements:
83
+ - - ! '>='
84
+ - !ruby/object:Gem::Version
85
+ version: '0'
86
+ type: :runtime
87
+ prerelease: false
88
+ version_requirements: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ! '>='
92
+ - !ruby/object:Gem::Version
93
+ version: '0'
78
94
  - !ruby/object:Gem::Dependency
79
95
  name: rake
80
96
  requirement: !ruby/object:Gem::Requirement
@@ -198,6 +214,7 @@ files:
198
214
  - spec/docker/container_spec.rb
199
215
  - spec/docker/image_spec.rb
200
216
  - spec/docker_spec.rb
217
+ - spec/fixtures/Dockerfile
201
218
  - spec/spec_helper.rb
202
219
  - spec/support/vcr.rb
203
220
  - spec/vcr/Docker/_info/returns_the_info_as_a_Hash.yml
@@ -217,6 +234,7 @@ files:
217
234
  - spec/vcr/Docker_Image/_all/when_the_HTTP_response_is_a_200/materializes_each_Container_into_a_Docker_Container.yml
218
235
  - spec/vcr/Docker_Image/_build/with_a_valid_Dockerfile/builds_an_image.yml
219
236
  - spec/vcr/Docker_Image/_build/with_an_invalid_Dockerfile/throws_a_UnexpectedResponseError.yml
237
+ - spec/vcr/Docker_Image/_build_from_file/with_a_valid_Dockerfile/builds_the_image.yml
220
238
  - spec/vcr/Docker_Image/_create_/when_the_Image_does_not_yet_exist_and_the_body_is_a_Hash/when_the_HTTP_request_returns_a_200/sets_the_id.yml
221
239
  - spec/vcr/Docker_Image/_create_from_file/when_the_file_does_exist/when_the_Image_has_not_been_created/creates_the_Image.yml
222
240
  - spec/vcr/Docker_Image/_history/when_the_Image_has_been_created/when_the_HTTP_response_status_is_200/returns_the_history_of_the_Image.yml
@@ -254,6 +272,7 @@ test_files:
254
272
  - spec/docker/container_spec.rb
255
273
  - spec/docker/image_spec.rb
256
274
  - spec/docker_spec.rb
275
+ - spec/fixtures/Dockerfile
257
276
  - spec/spec_helper.rb
258
277
  - spec/support/vcr.rb
259
278
  - spec/vcr/Docker/_info/returns_the_info_as_a_Hash.yml
@@ -273,6 +292,7 @@ test_files:
273
292
  - spec/vcr/Docker_Image/_all/when_the_HTTP_response_is_a_200/materializes_each_Container_into_a_Docker_Container.yml
274
293
  - spec/vcr/Docker_Image/_build/with_a_valid_Dockerfile/builds_an_image.yml
275
294
  - spec/vcr/Docker_Image/_build/with_an_invalid_Dockerfile/throws_a_UnexpectedResponseError.yml
295
+ - spec/vcr/Docker_Image/_build_from_file/with_a_valid_Dockerfile/builds_the_image.yml
276
296
  - spec/vcr/Docker_Image/_create_/when_the_Image_does_not_yet_exist_and_the_body_is_a_Hash/when_the_HTTP_request_returns_a_200/sets_the_id.yml
277
297
  - spec/vcr/Docker_Image/_create_from_file/when_the_file_does_exist/when_the_Image_has_not_been_created/creates_the_Image.yml
278
298
  - spec/vcr/Docker_Image/_history/when_the_Image_has_been_created/when_the_HTTP_response_status_is_200/returns_the_history_of_the_Image.yml
@@ -281,3 +301,4 @@ test_files:
281
301
  - spec/vcr/Docker_Image/_remove/when_the_Image_has_been_created/when_the_HTTP_response_status_is_204/nils_out_the_id.yml
282
302
  - spec/vcr/Docker_Image/_search/when_the_HTTP_response_is_a_200/materializes_each_Container_into_a_Docker_Container.yml
283
303
  - spec/vcr/Docker_Image/_tag/when_the_Image_has_been_created/when_the_HTTP_response_status_is_200/tags_the_image_with_the_repo_name.yml
304
+ has_rdoc: