vagrant-ganeti 0.0.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.
- data/.gitignore +17 -0
- data/Gemfile +12 -0
- data/LICENSE +8 -0
- data/LICENSE.txt +22 -0
- data/README.md +137 -0
- data/Rakefile +23 -0
- data/example_box/README.md +13 -0
- data/example_box/Vagrantfile +8 -0
- data/example_box/ganeti.box +0 -0
- data/example_box/metadata.json +3 -0
- data/lib/vagrant-plugin-ganeti/action/connect_ganeti.rb +70 -0
- data/lib/vagrant-plugin-ganeti/action/is_created.rb +18 -0
- data/lib/vagrant-plugin-ganeti/action/is_reachable.rb +18 -0
- data/lib/vagrant-plugin-ganeti/action/message_already_created.rb +16 -0
- data/lib/vagrant-plugin-ganeti/action/message_not_created.rb +16 -0
- data/lib/vagrant-plugin-ganeti/action/message_not_reachable.rb +16 -0
- data/lib/vagrant-plugin-ganeti/action/message_will_not_destroy.rb +16 -0
- data/lib/vagrant-plugin-ganeti/action/read_ssh_info.rb +32 -0
- data/lib/vagrant-plugin-ganeti/action/read_state.rb +84 -0
- data/lib/vagrant-plugin-ganeti/action/remove_instance.rb +26 -0
- data/lib/vagrant-plugin-ganeti/action/run_instance.rb +76 -0
- data/lib/vagrant-plugin-ganeti/action/sync_folders.rb +85 -0
- data/lib/vagrant-plugin-ganeti/action/timed_provision.rb +22 -0
- data/lib/vagrant-plugin-ganeti/action/unlink_server.rb +30 -0
- data/lib/vagrant-plugin-ganeti/action/warn_networks.rb +19 -0
- data/lib/vagrant-plugin-ganeti/action.rb +137 -0
- data/lib/vagrant-plugin-ganeti/config.rb +308 -0
- data/lib/vagrant-plugin-ganeti/errors.rb +19 -0
- data/lib/vagrant-plugin-ganeti/plugin.rb +73 -0
- data/lib/vagrant-plugin-ganeti/provider.rb +50 -0
- data/lib/vagrant-plugin-ganeti/util/ganeti_client.rb +142 -0
- data/lib/vagrant-plugin-ganeti/util/timer.rb +17 -0
- data/lib/vagrant-plugin-ganeti/version.rb +5 -0
- data/lib/vagrant-plugin-ganeti.rb +19 -0
- data/locales/en.yml +81 -0
- data/vagrant-plugin-ganeti.gemspec +57 -0
- metadata +163 -0
@@ -0,0 +1,85 @@
|
|
1
|
+
require "log4r"
|
2
|
+
|
3
|
+
require "vagrant/util/subprocess"
|
4
|
+
|
5
|
+
require "vagrant/util/scoped_hash_override"
|
6
|
+
|
7
|
+
require "vagrant/util/which"
|
8
|
+
|
9
|
+
module VagrantPlugins
|
10
|
+
module GANETI
|
11
|
+
module Action
|
12
|
+
# This middleware uses `rsync` to sync the folders over to the
|
13
|
+
# Ganeti instance.
|
14
|
+
class SyncFolders
|
15
|
+
include Vagrant::Util::ScopedHashOverride
|
16
|
+
|
17
|
+
def initialize(app, env)
|
18
|
+
@app = app
|
19
|
+
@logger = Log4r::Logger.new("vagrant_ganeti::action::sync_folders")
|
20
|
+
end
|
21
|
+
|
22
|
+
def call(env)
|
23
|
+
@app.call(env)
|
24
|
+
|
25
|
+
ssh_info = env[:machine].ssh_info
|
26
|
+
|
27
|
+
env[:machine].config.vm.synced_folders.each do |id, data|
|
28
|
+
data = scoped_hash_override(data, :ganeti)
|
29
|
+
|
30
|
+
# Ignore disabled shared folders
|
31
|
+
next if data[:disabled]
|
32
|
+
|
33
|
+
unless Vagrant::Util::Which.which('rsync')
|
34
|
+
env[:ui].warn(I18n.t('vagrant_ganeti.rsync_not_found_warning'))
|
35
|
+
break
|
36
|
+
end
|
37
|
+
|
38
|
+
hostpath = File.expand_path(data[:hostpath], env[:root_path])
|
39
|
+
guestpath = data[:guestpath]
|
40
|
+
|
41
|
+
# Make sure there is a trailing slash on the host path to
|
42
|
+
# avoid creating an additional directory with rsync
|
43
|
+
hostpath = "#{hostpath}/" if hostpath !~ /\/$/
|
44
|
+
|
45
|
+
# on windows rsync.exe requires cygdrive-style paths
|
46
|
+
if Vagrant::Util::Platform.windows?
|
47
|
+
hostpath = hostpath.gsub(/^(\w):/) { "/cygdrive/#{$1}" }
|
48
|
+
end
|
49
|
+
|
50
|
+
env[:ui].info(I18n.t("vagrant_ganeti.rsync_folder",
|
51
|
+
:hostpath => hostpath,
|
52
|
+
:guestpath => guestpath))
|
53
|
+
|
54
|
+
# Create the guest path
|
55
|
+
env[:machine].communicate.sudo("mkdir -p '#{guestpath}'")
|
56
|
+
env[:machine].communicate.sudo(
|
57
|
+
"chown #{ssh_info[:username]} '#{guestpath}'")
|
58
|
+
|
59
|
+
# Rsync over to the guest path using the SSH info
|
60
|
+
command = [
|
61
|
+
"rsync", "--verbose", "--archive", "-z",
|
62
|
+
"--exclude", ".vagrant/",
|
63
|
+
"-e", "ssh -p #{ssh_info[:port]} -o StrictHostKeyChecking=no -i '#{ssh_info[:private_key_path]}'",
|
64
|
+
hostpath,
|
65
|
+
"#{ssh_info[:username]}@#{ssh_info[:host]}:#{guestpath}"]
|
66
|
+
|
67
|
+
# we need to fix permissions when using rsync.exe on windows, see
|
68
|
+
# http://stackoverflow.com/questions/5798807/rsync-permission-denied-created-directories-have-no-permissions
|
69
|
+
if Vagrant::Util::Platform.windows?
|
70
|
+
command.insert(1, "--chmod", "ugo=rwX")
|
71
|
+
end
|
72
|
+
|
73
|
+
r = Vagrant::Util::Subprocess.execute(*command)
|
74
|
+
if r.exit_code != 0
|
75
|
+
raise Errors::RsyncError,
|
76
|
+
:guestpath => guestpath,
|
77
|
+
:hostpath => hostpath,
|
78
|
+
:stderr => r.stderr
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require "vagrant-ganeti/util/timer"
|
2
|
+
|
3
|
+
module VagrantPlugins
|
4
|
+
module GANETI
|
5
|
+
module Action
|
6
|
+
# This is the same as the builtin provision except it times the
|
7
|
+
# provisioner runs.
|
8
|
+
class TimedProvision < Vagrant::Action::Builtin::Provision
|
9
|
+
def run_provisioner(env, name, p)
|
10
|
+
timer = Util::Timer.time do
|
11
|
+
super
|
12
|
+
end
|
13
|
+
|
14
|
+
env[:metrics] ||= {}
|
15
|
+
env[:metrics]["provisioner_times"] ||= []
|
16
|
+
env[:metrics]["provisioner_times"] << [name, timer]
|
17
|
+
puts "Done Timed"
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
require "log4r"
|
2
|
+
|
3
|
+
module VagrantPlugins
|
4
|
+
module GANETI
|
5
|
+
module Action
|
6
|
+
# "unlink" vagrant and the managed server
|
7
|
+
class UnlinkServer
|
8
|
+
|
9
|
+
def initialize(app, env)
|
10
|
+
@app = app
|
11
|
+
@logger = Log4r::Logger.new("vagrant_ganeti::action::unlink_server")
|
12
|
+
end
|
13
|
+
|
14
|
+
def call(env)
|
15
|
+
|
16
|
+
server = env[:machine].id
|
17
|
+
|
18
|
+
# "Unlink"
|
19
|
+
env[:ui].info(I18n.t("vagrant_ganeti.unlinking_server", :host => server))
|
20
|
+
env[:ui].info(" -- Server: #{server}")
|
21
|
+
|
22
|
+
# set machine id to nil
|
23
|
+
env[:machine].id = nil
|
24
|
+
|
25
|
+
@app.call(env)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module VagrantPlugins
|
2
|
+
module GANETI
|
3
|
+
module Action
|
4
|
+
class WarnNetworks
|
5
|
+
def initialize(app, env)
|
6
|
+
@app = app
|
7
|
+
end
|
8
|
+
|
9
|
+
def call(env)
|
10
|
+
if env[:machine].config.vm.networks.length > 0
|
11
|
+
env[:ui].warn(I18n.t("vagrant_ganeti.warn_networks"))
|
12
|
+
end
|
13
|
+
|
14
|
+
@app.call(env)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,137 @@
|
|
1
|
+
require "pathname"
|
2
|
+
|
3
|
+
require "vagrant/action/builder"
|
4
|
+
|
5
|
+
module VagrantPlugins
|
6
|
+
module GANETI
|
7
|
+
module Action
|
8
|
+
# Include the built-in modules so we can use them as top-level things.
|
9
|
+
include Vagrant::Action::Builtin
|
10
|
+
|
11
|
+
# This action is called to establish linkage between vagrant and the Ganeti
|
12
|
+
def self.action_up
|
13
|
+
Vagrant::Action::Builder.new.tap do |b|
|
14
|
+
b.use HandleBoxUrl
|
15
|
+
b.use ConfigValidate
|
16
|
+
b.use WarnNetworks
|
17
|
+
b.use ConnectGANETI
|
18
|
+
b.use RunInstance
|
19
|
+
#b.use LinkServer
|
20
|
+
=begin
|
21
|
+
b.use HandleBoxUrl
|
22
|
+
b.use ConfigValidate
|
23
|
+
b.use Call, IsReachable do |env, b2|
|
24
|
+
if env[:result]
|
25
|
+
b2.use !MessageNotReachable
|
26
|
+
next
|
27
|
+
end
|
28
|
+
|
29
|
+
b2.use Provision
|
30
|
+
b2.use SyncFolders
|
31
|
+
b2.use WarnNetworks
|
32
|
+
b2.use LinkServer
|
33
|
+
end
|
34
|
+
=end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
|
39
|
+
def self.action_destroy
|
40
|
+
Vagrant::Action::Builder.new.tap do |b|
|
41
|
+
b.use Call, DestroyConfirm do |env, b2|
|
42
|
+
if env[:result]
|
43
|
+
b2.use ConfigValidate
|
44
|
+
b2.use ConnectGANETI
|
45
|
+
b2.use RemoveInstance
|
46
|
+
else
|
47
|
+
b2.use MessageWillNotDestroy
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
# This action is called when `vagrant provision` is called.
|
54
|
+
def self.action_provision
|
55
|
+
Vagrant::Action::Builder.new.tap do |b|
|
56
|
+
b.use ConfigValidate
|
57
|
+
b.use WarnNetworks
|
58
|
+
b.use Call, IsCreated do |env, b2|
|
59
|
+
if !env[:result]
|
60
|
+
b2.use MessageNotReachable
|
61
|
+
next
|
62
|
+
end
|
63
|
+
|
64
|
+
b2.use Provision
|
65
|
+
b2.use SyncFolders
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
# This action is called to read the state of the machine. The
|
71
|
+
# resulting state is expected to be put into the `:machine_state_id`
|
72
|
+
# key.
|
73
|
+
def self.action_read_state
|
74
|
+
Vagrant::Action::Builder.new.tap do |b|
|
75
|
+
b.use ConfigValidate
|
76
|
+
b.use ReadState
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
# This action is called to SSH into the machine.
|
81
|
+
def self.action_ssh
|
82
|
+
Vagrant::Action::Builder.new.tap do |b|
|
83
|
+
b.use ConfigValidate
|
84
|
+
b.use WarnNetworks
|
85
|
+
b.use Call, IsCreated do |env, b2|
|
86
|
+
if !env[:result]
|
87
|
+
b2.use MessageNotReachable
|
88
|
+
next
|
89
|
+
end
|
90
|
+
|
91
|
+
b2.use SSHExec
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
# This action is called to read the SSH info of the machine. The
|
97
|
+
# resulting state is expected to be put into the `:machine_ssh_info`
|
98
|
+
# key.
|
99
|
+
def self.action_read_ssh_info
|
100
|
+
Vagrant::Action::Builder.new.tap do |b|
|
101
|
+
b.use ConfigValidate
|
102
|
+
# b.use ConnectGANETI
|
103
|
+
b.use ReadSSHInfo
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
def self.action_ssh_run
|
108
|
+
Vagrant::Action::Builder.new.tap do |b|
|
109
|
+
b.use ConfigValidate
|
110
|
+
b.use WarnNetworks
|
111
|
+
b.use Call, IsCreated do |env, b2|
|
112
|
+
if !env[:result]
|
113
|
+
b2.use MessageNotReachable
|
114
|
+
next
|
115
|
+
end
|
116
|
+
|
117
|
+
b2.use SSHRun
|
118
|
+
end
|
119
|
+
end
|
120
|
+
end
|
121
|
+
|
122
|
+
|
123
|
+
# The autoload farm
|
124
|
+
action_root = Pathname.new(File.expand_path("../action", __FILE__))
|
125
|
+
autoload :ConnectGANETI, action_root.join("connect_ganeti")
|
126
|
+
autoload :IsReachable, action_root.join("is_reachable")
|
127
|
+
autoload :IsCreated, action_root.join("is_created")
|
128
|
+
autoload :MessageNotReachable, action_root.join("message_not_reachable")
|
129
|
+
autoload :ReadState, action_root.join("read_state")
|
130
|
+
autoload :ReadSSHInfo, action_root.join("read_ssh_info")
|
131
|
+
autoload :SyncFolders, action_root.join("sync_folders")
|
132
|
+
autoload :WarnNetworks, action_root.join("warn_networks")
|
133
|
+
autoload :RunInstance, action_root.join("run_instance")
|
134
|
+
autoload :RemoveInstance, action_root.join("remove_instance")
|
135
|
+
end
|
136
|
+
end
|
137
|
+
end
|
@@ -0,0 +1,308 @@
|
|
1
|
+
require "vagrant"
|
2
|
+
|
3
|
+
module VagrantPlugins
|
4
|
+
module GANETI
|
5
|
+
class Config < Vagrant.plugin("2", :config)
|
6
|
+
# The username for accessing GANETI.
|
7
|
+
#
|
8
|
+
# @return [String]
|
9
|
+
attr_accessor :rapi_user
|
10
|
+
|
11
|
+
# The password for accessing GANETI.
|
12
|
+
#
|
13
|
+
# @return [String]
|
14
|
+
attr_accessor :rapi_pass
|
15
|
+
|
16
|
+
# The Host Detail
|
17
|
+
#
|
18
|
+
# @return [String]
|
19
|
+
attr_accessor :cluster
|
20
|
+
|
21
|
+
# The timeout to wait for an instance to become ready.
|
22
|
+
#
|
23
|
+
# @return [Fixnum]
|
24
|
+
attr_accessor :instance_ready_timeout
|
25
|
+
|
26
|
+
|
27
|
+
# The version of the GANETI api to use
|
28
|
+
#
|
29
|
+
# @return [String]
|
30
|
+
attr_accessor :version
|
31
|
+
|
32
|
+
|
33
|
+
# The name of the OS to use.
|
34
|
+
#
|
35
|
+
# @return [String]
|
36
|
+
attr_accessor :os_type
|
37
|
+
|
38
|
+
# The name of the OS to use.
|
39
|
+
#
|
40
|
+
# @return [String]
|
41
|
+
attr_accessor :disk_template
|
42
|
+
|
43
|
+
# An array of hash of disk sizes
|
44
|
+
#
|
45
|
+
# @return [{hash }]
|
46
|
+
attr_accessor :disks
|
47
|
+
|
48
|
+
# The name of the Instance
|
49
|
+
#
|
50
|
+
# @return [String]
|
51
|
+
attr_accessor :instance_name
|
52
|
+
|
53
|
+
# Mode of Creation
|
54
|
+
#
|
55
|
+
# @return [String]
|
56
|
+
attr_accessor :mode
|
57
|
+
|
58
|
+
# Network Configurations
|
59
|
+
#
|
60
|
+
# @return [{hash}]
|
61
|
+
attr_accessor :nics
|
62
|
+
|
63
|
+
# The name of the Primary Node
|
64
|
+
#
|
65
|
+
# @return [String]
|
66
|
+
attr_accessor :pnode
|
67
|
+
|
68
|
+
# The name of the Secondary Node for DRBD template
|
69
|
+
#
|
70
|
+
# @return [String]
|
71
|
+
attr_accessor :snode
|
72
|
+
|
73
|
+
# The name of the Iallocatoy
|
74
|
+
#
|
75
|
+
# @return [String]
|
76
|
+
attr_accessor :iallocator
|
77
|
+
|
78
|
+
# Memory Configurations in MB's
|
79
|
+
#
|
80
|
+
# @return [String]
|
81
|
+
attr_accessor :memory
|
82
|
+
|
83
|
+
# VCPU configuration
|
84
|
+
#
|
85
|
+
# @return [String]
|
86
|
+
attr_accessor :vcpus
|
87
|
+
|
88
|
+
# Name Check
|
89
|
+
#
|
90
|
+
# @return [Boolean]
|
91
|
+
attr_accessor :name_check
|
92
|
+
|
93
|
+
# IP Check configuration
|
94
|
+
#
|
95
|
+
# @return [Boolean]
|
96
|
+
attr_accessor :ip_check
|
97
|
+
|
98
|
+
# hvparam Configs
|
99
|
+
#
|
100
|
+
# @return [String]
|
101
|
+
attr_accessor :hvparam
|
102
|
+
|
103
|
+
# hvparam Configs
|
104
|
+
#
|
105
|
+
# @return [String]
|
106
|
+
attr_accessor :boot_order
|
107
|
+
|
108
|
+
# hvparam Configs
|
109
|
+
#
|
110
|
+
# @return [String]
|
111
|
+
attr_accessor :cdrom_image_path
|
112
|
+
|
113
|
+
# hvparam Configs
|
114
|
+
#
|
115
|
+
# @return [String]
|
116
|
+
attr_accessor :nic_type
|
117
|
+
|
118
|
+
# hvparam Configs
|
119
|
+
#
|
120
|
+
# @return [String]
|
121
|
+
attr_accessor :disk_type
|
122
|
+
|
123
|
+
# hvparam Configs
|
124
|
+
#
|
125
|
+
# @return [String]
|
126
|
+
attr_accessor :cpu_type
|
127
|
+
|
128
|
+
# hvparam Configs
|
129
|
+
#
|
130
|
+
# @return [String]
|
131
|
+
attr_accessor :kernel_path
|
132
|
+
|
133
|
+
# hvparam Configs
|
134
|
+
#
|
135
|
+
# @return [String]
|
136
|
+
attr_accessor :kernel_args
|
137
|
+
|
138
|
+
# hvparam Configs
|
139
|
+
#
|
140
|
+
# @return [String]
|
141
|
+
attr_accessor :initrd_path
|
142
|
+
|
143
|
+
# hvparam Configs
|
144
|
+
#
|
145
|
+
# @return [String]
|
146
|
+
attr_accessor :root_path
|
147
|
+
|
148
|
+
# hvparam Configs
|
149
|
+
#
|
150
|
+
# @return [String]
|
151
|
+
attr_accessor :serial_console
|
152
|
+
|
153
|
+
# hvparam Configs
|
154
|
+
#
|
155
|
+
# @return [String]
|
156
|
+
attr_accessor :kvm_flag
|
157
|
+
|
158
|
+
def initialize()
|
159
|
+
@rapi_user = UNSET_VALUE
|
160
|
+
@rapi_pass = UNSET_VALUE
|
161
|
+
@cluster = UNSET_VALUE
|
162
|
+
@version = 2
|
163
|
+
@os_type = UNSET_VALUE
|
164
|
+
@disk_template = UNSET_VALUE
|
165
|
+
@disks = UNSET_VALUE
|
166
|
+
@instance_name = UNSET_VALUE
|
167
|
+
@mode = UNSET_VALUE
|
168
|
+
@nics = UNSET_VALUE
|
169
|
+
@pnode = UNSET_VALUE
|
170
|
+
@snode = UNSET_VALUE
|
171
|
+
@iallocator = UNSET_VALUE
|
172
|
+
@memory = UNSET_VALUE
|
173
|
+
@vcpus = UNSET_VALUE
|
174
|
+
@ip_check = UNSET_VALUE
|
175
|
+
@name_check = UNSET_VALUE
|
176
|
+
@boot_order = UNSET_VALUE
|
177
|
+
@cdrom_image_path = UNSET_VALUE
|
178
|
+
@nic_type = UNSET_VALUE
|
179
|
+
@disk_type = UNSET_VALUE
|
180
|
+
@cpu_type = UNSET_VALUE
|
181
|
+
@kernel_path = UNSET_VALUE
|
182
|
+
@kernel_args = UNSET_VALUE
|
183
|
+
@initrd_path = UNSET_VALUE
|
184
|
+
@root_path = UNSET_VALUE
|
185
|
+
@serial_console = UNSET_VALUE
|
186
|
+
@kvm_flag = UNSET_VALUE
|
187
|
+
@__finalized = false
|
188
|
+
end
|
189
|
+
|
190
|
+
def finalize!
|
191
|
+
# Username and password for the Ganei RAPI must be set .
|
192
|
+
@rapi_user = nil if @rapi_user == UNSET_VALUE
|
193
|
+
@rapi_pass = nil if @rapi_pass == UNSET_VALUE
|
194
|
+
|
195
|
+
# host must be nil, since we can't default that
|
196
|
+
@cluster = nil if @cluster == UNSET_VALUE
|
197
|
+
|
198
|
+
# OS_NAME must be nil, since we can't default that
|
199
|
+
@os_type = nil if @os_type == UNSET_VALUE
|
200
|
+
|
201
|
+
# disk_template since we can't default that
|
202
|
+
@disk_template = "plain" if @disk_template == UNSET_VALUE
|
203
|
+
|
204
|
+
# disks must be nil, since we can't default that
|
205
|
+
@disks = [{"size"=>"8000"}] if @disks == UNSET_VALUE
|
206
|
+
|
207
|
+
# instance_name must be nil, since we can't default that
|
208
|
+
@instance_name = nil if @instance_name == UNSET_VALUE
|
209
|
+
|
210
|
+
# mode must be nil, since we can't default that
|
211
|
+
@mode = "create" if @mode == UNSET_VALUE
|
212
|
+
|
213
|
+
# nics must be nil, since we can't default that
|
214
|
+
@nics = nil if @nics == UNSET_VALUE
|
215
|
+
|
216
|
+
# pnode must be nil, since we can't default that
|
217
|
+
@pnode = nil if @pnode == UNSET_VALUE
|
218
|
+
|
219
|
+
# snode must be nil, since we can't default that
|
220
|
+
@snode = nil if @snode == UNSET_VALUE
|
221
|
+
|
222
|
+
# iallocator Get default from ganeti cluster
|
223
|
+
@iallocator = "__DEFAULT__" if @iallocator == UNSET_VALUE
|
224
|
+
|
225
|
+
# memory must be nil, since we can't default that
|
226
|
+
@memory = nil if @memory == UNSET_VALUE
|
227
|
+
|
228
|
+
# vcpu must be nil, since we can't default that
|
229
|
+
@vcpus = nil if @vcpus == UNSET_VALUE
|
230
|
+
|
231
|
+
# ip_check defaults to True
|
232
|
+
@ip_check = true if @ip_check == UNSET_VALUE
|
233
|
+
|
234
|
+
# name_check defaults to True
|
235
|
+
@name_check = true if @name_check == UNSET_VALUE
|
236
|
+
|
237
|
+
# boot_order defaults to Nil
|
238
|
+
@boot_order = nil if @boot_order == UNSET_VALUE
|
239
|
+
|
240
|
+
# cdrom_image_path to Nil
|
241
|
+
@cdrom_image_path= nil if @cdrom_image_path == UNSET_VALUE
|
242
|
+
|
243
|
+
# nic_type defaults to nil
|
244
|
+
@nic_type = nil if @nic_type == UNSET_VALUE
|
245
|
+
|
246
|
+
# disk_type defaults to nil
|
247
|
+
@disk_type = nil if @disk_type == UNSET_VALUE
|
248
|
+
|
249
|
+
# cpu_type defaults to nil
|
250
|
+
@cpu_type = nil if @cpu_type == UNSET_VALUE
|
251
|
+
|
252
|
+
# kernel_path defaults to nil
|
253
|
+
@kernel_path = nil if @kernel_path == UNSET_VALUE
|
254
|
+
|
255
|
+
# kernel_args defaults to nil
|
256
|
+
@kernel_args = nil if @kernel_args == UNSET_VALUE
|
257
|
+
|
258
|
+
|
259
|
+
# initrd_path defaults to nil
|
260
|
+
@initrd_path = nil if @initrd_path == UNSET_VALUE
|
261
|
+
|
262
|
+
# root_path_path defaults to nil
|
263
|
+
@root_path = nil if @root_path == UNSET_VALUE
|
264
|
+
|
265
|
+
# serial_console defaults to nil
|
266
|
+
@serial_console = nil if @serial_console == UNSET_VALUE
|
267
|
+
|
268
|
+
# kvm_flag defaults to nil
|
269
|
+
@kvm_flag = nil if @kvm_flag == UNSET_VALUE
|
270
|
+
|
271
|
+
# Set the default timeout for waiting for an instance to be ready
|
272
|
+
@instance_ready_timeout = 120 if @instance_ready_timeout == UNSET_VALUE
|
273
|
+
|
274
|
+
@version = nil if @version == UNSET_VALUE
|
275
|
+
|
276
|
+
|
277
|
+
# Mark that we finalized
|
278
|
+
@__finalized = true
|
279
|
+
end
|
280
|
+
|
281
|
+
|
282
|
+
def validate(machine)
|
283
|
+
errors = _detected_errors
|
284
|
+
|
285
|
+
errors << I18n.t("vagrant_ganeti.config.username_required") if @rapi_user.nil?
|
286
|
+
errors << I18n.t("vagrant_ganeti.config.password_required") if @rapi_pass.nil?
|
287
|
+
errors << I18n.t("vagrant_ganeti.config.host_required") if @cluster.nil?
|
288
|
+
errors << I18n.t("vagrant_ganeti.config.os_name_required") if @os_type.nil?
|
289
|
+
errors << I18n.t("vagrant_ganeti.config.disk_template_required") if @disk_template.nil?
|
290
|
+
errors << I18n.t("vagrant_ganeti.config.disks_required") if @disks == nil
|
291
|
+
errors << I18n.t("vagrant_ganeti.config.instance_name_required") if @instance_name.nil?
|
292
|
+
errors << I18n.t("vagrant_ganeti.config.mode_required") if @mode.nil?
|
293
|
+
errors << I18n.t("vagrant_ganeti.config.nics_required") if @nics.nil?
|
294
|
+
errors << I18n.t("vagrant_ganeti.config.pnode_required") if @pnode.nil? and @iallocator.nil?
|
295
|
+
errors << I18n.t("vagrant_ganeti.config.snode_required") if @snode.nil? and @disk_template == "drbd" and @iallocator.nil?
|
296
|
+
{ "GANETI Provider" => errors }
|
297
|
+
|
298
|
+
end
|
299
|
+
def get_config()
|
300
|
+
if !@__finalized
|
301
|
+
raise "Configuration must be finalized before calling this method."
|
302
|
+
end
|
303
|
+
|
304
|
+
self
|
305
|
+
end
|
306
|
+
end
|
307
|
+
end
|
308
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
require "vagrant"
|
2
|
+
|
3
|
+
module VagrantPlugins
|
4
|
+
module GANETI
|
5
|
+
module Errors
|
6
|
+
class VagrantGANETIError < Vagrant::Errors::VagrantError
|
7
|
+
error_namespace("vagrant_ganeti.errors")
|
8
|
+
end
|
9
|
+
|
10
|
+
class InstanceReadyTimeout < VagrantGANETIError
|
11
|
+
error_key(:instance_ready_timeout)
|
12
|
+
end
|
13
|
+
|
14
|
+
class RsyncError < VagrantGANETIError
|
15
|
+
error_key(:rsync_error)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,73 @@
|
|
1
|
+
begin
|
2
|
+
require "vagrant"
|
3
|
+
rescue LoadError
|
4
|
+
raise "The Vagrant GANETI plugin must be run within Vagrant."
|
5
|
+
end
|
6
|
+
|
7
|
+
# This is a sanity check to make sure no one is attempting to install
|
8
|
+
# this into an early Vagrant version.
|
9
|
+
if Vagrant::VERSION < "1.2.0"
|
10
|
+
raise "The Vagrant GANETI plugin is only compatible with Vagrant 1.2+"
|
11
|
+
end
|
12
|
+
|
13
|
+
module VagrantPlugins
|
14
|
+
module GANETI
|
15
|
+
class Plugin < Vagrant.plugin("2")
|
16
|
+
name "GANETI"
|
17
|
+
description <<-DESC
|
18
|
+
This plugin installs a provider that allows Vagrant to manage
|
19
|
+
machines in GANETI clusters.
|
20
|
+
DESC
|
21
|
+
|
22
|
+
config(:ganeti, :provider) do
|
23
|
+
require_relative "config"
|
24
|
+
Config
|
25
|
+
end
|
26
|
+
|
27
|
+
provider(:ganeti, parallel: true) do
|
28
|
+
# Setup logging and i18n
|
29
|
+
setup_logging
|
30
|
+
setup_i18n
|
31
|
+
|
32
|
+
# Return the provider
|
33
|
+
require_relative "provider"
|
34
|
+
Provider
|
35
|
+
end
|
36
|
+
|
37
|
+
# This initializes the internationalization strings.
|
38
|
+
def self.setup_i18n
|
39
|
+
I18n.load_path << File.expand_path("locales/en.yml", GANETI.source_root)
|
40
|
+
I18n.reload!
|
41
|
+
end
|
42
|
+
|
43
|
+
# This sets up our log level to be whatever VAGRANT_LOG is.
|
44
|
+
def self.setup_logging
|
45
|
+
require "log4r"
|
46
|
+
|
47
|
+
level = nil
|
48
|
+
begin
|
49
|
+
level = Log4r.const_get(ENV["VAGRANT_LOG"].upcase)
|
50
|
+
rescue NameError
|
51
|
+
# This means that the logging constant wasn't found,
|
52
|
+
# which is fine. We just keep `level` as `nil`. But
|
53
|
+
# we tell the user.
|
54
|
+
level = nil
|
55
|
+
end
|
56
|
+
|
57
|
+
# Some constants, such as "true" resolve to booleans, so the
|
58
|
+
# above error checking doesn't catch it. This will check to make
|
59
|
+
# sure that the log level is an integer, as Log4r requires.
|
60
|
+
level = nil if !level.is_a?(Integer)
|
61
|
+
|
62
|
+
# Set the logging level on all "vagrant" namespaced
|
63
|
+
# logs as long as we have a valid level.
|
64
|
+
if level
|
65
|
+
logger = Log4r::Logger.new("vagrant_plugin_ganeti")
|
66
|
+
logger.outputters = Log4r::Outputter.stderr
|
67
|
+
logger.level = level
|
68
|
+
logger = nil
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|