vagrant-prison 0.0.4 → 0.1.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.
- data/README.md +44 -1
- data/lib/vagrant/prison.rb +108 -23
- data/lib/vagrant/prison/version.rb +1 -1
- data/vagrant-prison.gemspec +1 -1
- metadata +4 -3
data/README.md
CHANGED
|
@@ -1,6 +1,37 @@
|
|
|
1
1
|
# Vagrant::Prison
|
|
2
2
|
|
|
3
3
|
Drive vagrant configuration directly from your test suite, rakefiles, etc.
|
|
4
|
+
Basically anywhere you can write ruby, you can drive Vagrant.
|
|
5
|
+
|
|
6
|
+
## Reasoning and Use Cases
|
|
7
|
+
|
|
8
|
+
When you create and configure a `Vagrantfile`, the internals of Vagrant coerce
|
|
9
|
+
this into a `Vagrant::Environment` object that has a number of properties.
|
|
10
|
+
Unfortunately, much of Vagrant's design runs under the expectation that all
|
|
11
|
+
this data comes from a `Vagrantfile` on disk in the current working directory,
|
|
12
|
+
and therefore `Vagrant::Environment` objects can't be created programmatically
|
|
13
|
+
-- a problem when you have a desire to create them dynamically and templating
|
|
14
|
+
Vagrantfiles all over the place isn't really a solution.
|
|
15
|
+
|
|
16
|
+
For example, if you want to maintain parity between configuration supplied to
|
|
17
|
+
Vagrant and your tool that uses Vagrant, or if you want to allow the user to
|
|
18
|
+
supply additional code to be injected into Vagrantfiles and ensure the code is
|
|
19
|
+
not only syntactically correct, but is evaluated in the right context.
|
|
20
|
+
Additionally prison objects can be modified and appended to post hoc, which has
|
|
21
|
+
some nice advantages from a flexibility standpoint.
|
|
22
|
+
|
|
23
|
+
You can also marshal `Vagrant::Prison` objects -- something you can't do with
|
|
24
|
+
`Vagrant::Environment`. What this is good for is left as an exercise to the
|
|
25
|
+
reader.
|
|
26
|
+
|
|
27
|
+
Vagrant::Prison is to Vagrant what unix jails are ... to unix. It fakes out
|
|
28
|
+
Vagrant well enough to think it's working with a traditional `Vagrantfile`, but
|
|
29
|
+
it's actually working with something emulating one, without actually modifying
|
|
30
|
+
the internals of Vagrant itself. It accomplishes this with recording proxies
|
|
31
|
+
that are played back to Vagrant when it starts.
|
|
32
|
+
|
|
33
|
+
Vagrant::Prison is **not** threadsafe. This is actually a limitation of
|
|
34
|
+
Vagrant, but there's nothing we can or will do to work around it.
|
|
4
35
|
|
|
5
36
|
## Installation
|
|
6
37
|
|
|
@@ -36,12 +67,24 @@ prison.configure do |config|
|
|
|
36
67
|
end
|
|
37
68
|
end
|
|
38
69
|
|
|
39
|
-
#
|
|
70
|
+
# here's a basic way to start your vms:
|
|
71
|
+
|
|
72
|
+
prison.start
|
|
73
|
+
|
|
74
|
+
# If you need more flexibility, all the internal Vagrant tooling works -- it
|
|
75
|
+
# has no idea it's working with a facsimile.
|
|
76
|
+
#
|
|
77
|
+
# note that if you don't set :ui_class here, it still works, it just provides
|
|
78
|
+
# no output.
|
|
40
79
|
Vagrant::Command::Up.new(
|
|
41
80
|
[],
|
|
42
81
|
prison.construct(:ui_class => Vagrant::UI::Basic)
|
|
43
82
|
).execute
|
|
44
83
|
|
|
84
|
+
#
|
|
85
|
+
# Since we've configured it to destroy on exit here, sleep until someone hits
|
|
86
|
+
# ^C.
|
|
87
|
+
#
|
|
45
88
|
begin
|
|
46
89
|
sleep
|
|
47
90
|
rescue Interrupt
|
data/lib/vagrant/prison.rb
CHANGED
|
@@ -16,6 +16,23 @@ EOF
|
|
|
16
16
|
|
|
17
17
|
class Vagrant::Prison
|
|
18
18
|
attr_reader :dir
|
|
19
|
+
# name this prison. only used for your needs to refer to later.
|
|
20
|
+
attr_accessor :name
|
|
21
|
+
|
|
22
|
+
def self.cleanup(dir, env)
|
|
23
|
+
Vagrant::Prison.new(dir, false, env).cleanup
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
# Prisons can't be marshalled because they contain a Vagrant::Environment,
|
|
27
|
+
# which has some properties about it that Marshal rejects. This routine takes
|
|
28
|
+
# the output of Vagrant::Prison#save and rebuilds the object.
|
|
29
|
+
def self._load(str)
|
|
30
|
+
hash = Marshal.load(str)
|
|
31
|
+
prison = new(hash[:dir], hash[:cleanup_on_exit])
|
|
32
|
+
prison.name = hash[:name]
|
|
33
|
+
prison.configure_environment(hash[:env_opts])
|
|
34
|
+
return prison
|
|
35
|
+
end
|
|
19
36
|
|
|
20
37
|
#
|
|
21
38
|
# Construct a new Vagrant sandbox. Takes two arguments: (the third should be
|
|
@@ -28,15 +45,33 @@ class Vagrant::Prison
|
|
|
28
45
|
# the program exits, or when this object is garbage collected, which ever
|
|
29
46
|
# comes first.
|
|
30
47
|
#
|
|
31
|
-
def initialize(dir=nil, cleanup_on_exit=true,
|
|
32
|
-
@dir
|
|
33
|
-
@initial_config
|
|
34
|
-
@
|
|
35
|
-
@cleanup_on_exit
|
|
48
|
+
def initialize(dir=nil, cleanup_on_exit=true, env_opts={})
|
|
49
|
+
@dir = dir ||= Dir.mktmpdir
|
|
50
|
+
@initial_config = nil
|
|
51
|
+
@env_opts = env_opts.merge(:cwd => @dir, :ui_class => Vagrant::UI::Basic)
|
|
52
|
+
@cleanup_on_exit = cleanup_on_exit
|
|
53
|
+
@name = "default"
|
|
36
54
|
end
|
|
37
55
|
|
|
38
|
-
|
|
39
|
-
|
|
56
|
+
#
|
|
57
|
+
# Return a marshalled representation of a Vagrant::Prison. This actually
|
|
58
|
+
# yields a marshalled array of the directory the prison lives in, and the
|
|
59
|
+
# options used for creating the Vagrant::Environment.
|
|
60
|
+
#
|
|
61
|
+
# This routine will raise if the environment has not been configured yet.
|
|
62
|
+
#
|
|
63
|
+
|
|
64
|
+
def _dump(level)
|
|
65
|
+
unless @env_opts
|
|
66
|
+
raise "This environment has not been configured/created! Cannot be dumped."
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
Marshal.dump({
|
|
70
|
+
:dir => @dir,
|
|
71
|
+
:cleanup_on_exit => @cleanup_on_exit,
|
|
72
|
+
:env_opts => @env_opts,
|
|
73
|
+
:name => @name
|
|
74
|
+
})
|
|
40
75
|
end
|
|
41
76
|
|
|
42
77
|
#
|
|
@@ -44,8 +79,11 @@ class Vagrant::Prison
|
|
|
44
79
|
# the directory will be deleted.
|
|
45
80
|
#
|
|
46
81
|
def cleanup
|
|
47
|
-
|
|
48
|
-
|
|
82
|
+
if File.directory?(dir)
|
|
83
|
+
return destroy && FileUtils.rm_r(dir)
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
return false
|
|
49
87
|
end
|
|
50
88
|
|
|
51
89
|
#
|
|
@@ -63,6 +101,13 @@ class Vagrant::Prison
|
|
|
63
101
|
@env_opts
|
|
64
102
|
end
|
|
65
103
|
|
|
104
|
+
#
|
|
105
|
+
# Returns the Vagrant::Environment, if any.
|
|
106
|
+
#
|
|
107
|
+
def env
|
|
108
|
+
@env
|
|
109
|
+
end
|
|
110
|
+
|
|
66
111
|
#
|
|
67
112
|
# Configures a Vagrantfile.
|
|
68
113
|
#
|
|
@@ -106,8 +151,8 @@ class Vagrant::Prison
|
|
|
106
151
|
# re-creating it.
|
|
107
152
|
#
|
|
108
153
|
def configure_environment(env_opts={})
|
|
109
|
-
@env_opts
|
|
110
|
-
@env
|
|
154
|
+
@env_opts.merge!(env_opts)
|
|
155
|
+
@env = Vagrant::Environment.new(@env_opts)
|
|
111
156
|
end
|
|
112
157
|
|
|
113
158
|
#
|
|
@@ -120,6 +165,10 @@ class Vagrant::Prison
|
|
|
120
165
|
# * if you set `cleanup_on_exit` in the constructor, runs `cleanup` on
|
|
121
166
|
# garbage collection of this object or program exit, which ever comes first.
|
|
122
167
|
#
|
|
168
|
+
# Note, if you supplied environment options here, they will merge into the
|
|
169
|
+
# ones supplied to the constructor, before the Vagrant::Environment was
|
|
170
|
+
# created.
|
|
171
|
+
#
|
|
123
172
|
def construct(env_opts={})
|
|
124
173
|
FileUtils.mkdir_p(dir)
|
|
125
174
|
|
|
@@ -134,20 +183,44 @@ class Vagrant::Prison
|
|
|
134
183
|
|
|
135
184
|
File.binwrite(File.join(dir, "Vagrantfile"), to_write)
|
|
136
185
|
|
|
137
|
-
if @cleanup_on_exit
|
|
138
|
-
# clean up after garbage collection or if the system exits
|
|
139
|
-
ObjectSpace.define_finalizer(self) do
|
|
140
|
-
Vagrant::Prison.cleanup(dir, env)
|
|
141
|
-
end
|
|
186
|
+
build_cleanup_hooks if @cleanup_on_exit
|
|
142
187
|
|
|
143
|
-
|
|
188
|
+
return @env
|
|
189
|
+
end
|
|
144
190
|
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
191
|
+
#
|
|
192
|
+
# Create the cleanup hooks that tell ruby to torch this prison on garbage
|
|
193
|
+
# collection or exit.
|
|
194
|
+
#
|
|
195
|
+
def build_cleanup_hooks
|
|
196
|
+
raise "Environment not configured!" unless @env
|
|
197
|
+
|
|
198
|
+
env = @env
|
|
199
|
+
|
|
200
|
+
# clean up after garbage collection or if the system exits
|
|
201
|
+
ObjectSpace.define_finalizer(self) do
|
|
202
|
+
Vagrant::Prison.cleanup(dir, env)
|
|
148
203
|
end
|
|
149
204
|
|
|
150
|
-
|
|
205
|
+
at_exit do
|
|
206
|
+
self.cleanup
|
|
207
|
+
end
|
|
208
|
+
end
|
|
209
|
+
|
|
210
|
+
#
|
|
211
|
+
# Start or 'up' the entire prison. Convenience Method. Will also construct
|
|
212
|
+
# the environment if it is not already constructed.
|
|
213
|
+
#
|
|
214
|
+
|
|
215
|
+
def start
|
|
216
|
+
construct unless @env
|
|
217
|
+
|
|
218
|
+
Dir.chdir(dir) do
|
|
219
|
+
Vagrant::Command::Up.new([], @env).execute
|
|
220
|
+
end
|
|
221
|
+
return true
|
|
222
|
+
rescue SystemExit => e
|
|
223
|
+
return e.status == 0
|
|
151
224
|
end
|
|
152
225
|
|
|
153
226
|
#
|
|
@@ -155,7 +228,19 @@ class Vagrant::Prison
|
|
|
155
228
|
# `cleanup` for a one-shot way to orchestrate that.
|
|
156
229
|
#
|
|
157
230
|
def destroy
|
|
158
|
-
|
|
159
|
-
|
|
231
|
+
require 'timeout'
|
|
232
|
+
Dir.chdir(dir) do
|
|
233
|
+
begin
|
|
234
|
+
Timeout.timeout(60) do
|
|
235
|
+
Vagrant::Command::Halt.new([], @env).execute rescue nil
|
|
236
|
+
end
|
|
237
|
+
rescue Timeout::Error
|
|
238
|
+
$stderr.puts "Timeout reached; forcing destroy"
|
|
239
|
+
end
|
|
240
|
+
Vagrant::Command::Destroy.new(%w[-f], @env).execute rescue nil
|
|
241
|
+
end
|
|
242
|
+
return true
|
|
243
|
+
rescue SystemExit => e
|
|
244
|
+
return e.status == 0
|
|
160
245
|
end
|
|
161
246
|
end
|
data/vagrant-prison.gemspec
CHANGED
|
@@ -10,7 +10,7 @@ Gem::Specification.new do |gem|
|
|
|
10
10
|
gem.email = ["erik+github@hollensbe.org"]
|
|
11
11
|
gem.description = %q{A programmatic way to configure and sandbox Vagrant}
|
|
12
12
|
gem.summary = %q{A programmatic way to configure and sandbox Vagrant}
|
|
13
|
-
gem.homepage = ""
|
|
13
|
+
gem.homepage = "https://github.com/chef-workflow/vagrant-prison"
|
|
14
14
|
|
|
15
15
|
gem.files = `git ls-files`.split($/)
|
|
16
16
|
gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: vagrant-prison
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.0
|
|
4
|
+
version: 0.1.0
|
|
5
5
|
prerelease:
|
|
6
6
|
platform: ruby
|
|
7
7
|
authors:
|
|
@@ -9,7 +9,7 @@ authors:
|
|
|
9
9
|
autorequire:
|
|
10
10
|
bindir: bin
|
|
11
11
|
cert_chain: []
|
|
12
|
-
date: 2012-
|
|
12
|
+
date: 2012-12-21 00:00:00.000000000 Z
|
|
13
13
|
dependencies:
|
|
14
14
|
- !ruby/object:Gem::Dependency
|
|
15
15
|
name: vagrant
|
|
@@ -43,7 +43,7 @@ files:
|
|
|
43
43
|
- lib/vagrant/prison/config_proxy.rb
|
|
44
44
|
- lib/vagrant/prison/version.rb
|
|
45
45
|
- vagrant-prison.gemspec
|
|
46
|
-
homepage:
|
|
46
|
+
homepage: https://github.com/chef-workflow/vagrant-prison
|
|
47
47
|
licenses: []
|
|
48
48
|
post_install_message:
|
|
49
49
|
rdoc_options: []
|
|
@@ -68,3 +68,4 @@ signing_key:
|
|
|
68
68
|
specification_version: 3
|
|
69
69
|
summary: A programmatic way to configure and sandbox Vagrant
|
|
70
70
|
test_files: []
|
|
71
|
+
has_rdoc:
|