vagrant-softlayer 0.3.1 → 0.3.2
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 +4 -4
- data/CHANGELOG.md +37 -24
- data/QUICKSTART.md +377 -0
- data/README.md +25 -20
- data/contrib/README.md +8 -1
- data/contrib/vagrant-softlayer-boxes +416 -408
- data/contrib/vagrant-softlayer-vlans +329 -0
- data/contrib/vagrantcloud/CENTOS_5_32.box +0 -0
- data/contrib/vagrantcloud/CENTOS_5_64.box +0 -0
- data/contrib/vagrantcloud/CENTOS_6_32.box +0 -0
- data/contrib/vagrantcloud/CENTOS_6_64.box +0 -0
- data/contrib/vagrantcloud/CENTOS_LATEST.box +0 -0
- data/contrib/vagrantcloud/CENTOS_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/CENTOS_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_5_32.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_5_64.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_6_32.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_6_64.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_LATEST.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/CLOUDLINUX_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_5_32.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_5_64.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_6_32.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_6_64.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_7_32.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_7_64.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_LATEST.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/DEBIAN_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/REDHAT_5_32.box +0 -0
- data/contrib/vagrantcloud/REDHAT_5_64.box +0 -0
- data/contrib/vagrantcloud/REDHAT_6_32.box +0 -0
- data/contrib/vagrantcloud/REDHAT_6_64.box +0 -0
- data/contrib/vagrantcloud/REDHAT_LATEST.box +0 -0
- data/contrib/vagrantcloud/REDHAT_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/REDHAT_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/SL_GENERIC.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_10_32.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_10_64.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_12_32.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_12_64.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_14_32.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_14_64.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_8_32.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_8_64.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_LATEST.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/UBUNTU_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/VYATTACE_6.5_64.box +0 -0
- data/contrib/vagrantcloud/VYATTACE_6.6_64.box +0 -0
- data/contrib/vagrantcloud/VYATTACE_LATEST.box +0 -0
- data/contrib/vagrantcloud/VYATTACE_LATEST_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-DC-SP2-1_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-DC-SP2-1_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-ENT-SP2-5_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-ENT-SP2-5_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-STD-SP2-5_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2003-STD-SP2-5_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-DC-R2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-DC-SP2_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-DC-SP2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-ENT-R2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-ENT-SP2_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-ENT-SP2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-STD-R2-SP1_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-STD-R2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-STD-SP2_32.box +0 -0
- data/contrib/vagrantcloud/WIN_2008-STD-SP2_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2012-DC_64.box +0 -0
- data/contrib/vagrantcloud/WIN_2012-STD_64.box +0 -0
- data/contrib/vagrantcloud/WIN_LATEST.box +0 -0
- data/contrib/vagrantcloud/WIN_LATEST_32.box +0 -0
- data/contrib/vagrantcloud/WIN_LATEST_64.box +0 -0
- data/lib/vagrant-softlayer/action.rb +20 -16
- data/lib/vagrant-softlayer/action/create_instance.rb +24 -8
- data/lib/vagrant-softlayer/action/setup_softlayer.rb +2 -1
- data/lib/vagrant-softlayer/action/sync_folders.rb +99 -99
- data/lib/vagrant-softlayer/action/wait_for_rebuild.rb +36 -36
- data/lib/vagrant-softlayer/config.rb +10 -2
- data/lib/vagrant-softlayer/errors.rb +33 -29
- data/lib/vagrant-softlayer/plugin.rb +77 -77
- data/lib/vagrant-softlayer/util/load_balancer.rb +103 -103
- data/lib/vagrant-softlayer/util/network.rb +75 -73
- data/lib/vagrant-softlayer/util/warden.rb +38 -38
- data/lib/vagrant-softlayer/version.rb +5 -5
- data/locales/en.yml +6 -0
- data/spec/vagrant-softlayer/config_spec.rb +4 -2
- data/vagrant-softlayer.gemspec +55 -55
- metadata +71 -2
data/README.md
CHANGED
@@ -79,26 +79,27 @@ See [Join load balancers](https://github.com/audiolize/vagrant-softlayer/wiki/Jo
|
|
79
79
|
|
80
80
|
### Instance Configuration
|
81
81
|
|
82
|
-
Parameter | Description | Default
|
83
|
-
------------------ |
|
84
|
-
`datacenter` | Datacenter shortname | First available
|
85
|
-
`dedicated` | Allocate a dedicated CCI (non-shared host) | false
|
86
|
-
`disk_capacity` | The capacity of each disk |
|
87
|
-
`domain` | The domain of the instance |
|
88
|
-
`
|
89
|
-
`
|
90
|
-
`
|
91
|
-
`
|
92
|
-
`
|
93
|
-
`
|
94
|
-
`
|
95
|
-
`
|
96
|
-
`
|
97
|
-
`
|
98
|
-
`
|
99
|
-
`
|
100
|
-
`
|
101
|
-
`
|
82
|
+
Parameter | Description | Default | Required
|
83
|
+
------------------ | -----------------------------------------------------------| ----------------| --------
|
84
|
+
`datacenter` | Datacenter shortname | First available | no
|
85
|
+
`dedicated` | Allocate a dedicated CCI (non-shared host) | false | no
|
86
|
+
`disk_capacity` | The capacity of each disk | | no **
|
87
|
+
`domain` | The domain of the instance | | yes
|
88
|
+
`force_private_ip` | Use private IP for communication even if public IP is set | false | no
|
89
|
+
`hostname` | The hostname of the instance | | yes *
|
90
|
+
`hourly_billing` | Hourly billing type (false for monthly) | true | no
|
91
|
+
`image_guid` | The global identifier for the compute or flex image to use | | no **
|
92
|
+
`local_disk` | Use a local disk (false for SAN) | true | no
|
93
|
+
`max_memory` | The amount of RAM of the instance in Mb | 1024 | no
|
94
|
+
`network_speed` | Network port speed in Mbps | 10 | no
|
95
|
+
`operating_system` | The instance operating system identifier | UBUNTU_LATEST | no **
|
96
|
+
`post_install` | URI of Post-install script to download | | no
|
97
|
+
`private_only` | Only create access to the private network | false | no
|
98
|
+
`ssh_key` | ID or label of the SSH key(s) to provision | | yes
|
99
|
+
`start_cpus` | The number of processors of the instance | 1 | no
|
100
|
+
`user_data` | User defined metadata string | | no
|
101
|
+
`vlan_private` | The ID, name or qualified name of the private VLAN | Auto-generated | no
|
102
|
+
`vlan_public` | The ID, name or qualified name of the public VLAN | Auto-generated | no
|
102
103
|
|
103
104
|
\* The `hostname` could be specified either using `config.vm.hostname` or the provider parameter.
|
104
105
|
|
@@ -208,6 +209,10 @@ Also, a bunch of aliases for the `ssh_key` parameter are provided for better sem
|
|
208
209
|
* `ssh_key_name`
|
209
210
|
* `ssh_key_names`
|
210
211
|
|
212
|
+
## Quick Start Guide
|
213
|
+
|
214
|
+
For those new to Vagrant, see the [Quick Start Guide](https://github.com/audiolize/vagrant-softlayer/blob/master/QUICKSTART.md).
|
215
|
+
|
211
216
|
## Development
|
212
217
|
|
213
218
|
To work on the `vagrant-softlayer` plugin, clone this repository out, and use
|
data/contrib/README.md
CHANGED
@@ -6,6 +6,13 @@ for each item will be kept below.
|
|
6
6
|
|
7
7
|
## List of Contrib Items
|
8
8
|
|
9
|
+
* `vagrantcloud` - Vagrant boxes used by Vagrant Cloud examples in the Quick Start
|
10
|
+
guide or for manual install locally without having to use `vagrant-softlayer-boxes`.
|
9
11
|
* `vagrant-softlayer-boxes` - Vagrant box creation tool which allows you to create
|
10
12
|
starter boxes from those offered in the SoftLayer API or from public/private compute
|
11
|
-
or flex images associated with your SoftLayer account.
|
13
|
+
or flex images associated with your SoftLayer account.
|
14
|
+
* `vagrant-softlayer-vlans` - SoftLayer vlan tool which allows you to list the data
|
15
|
+
for all SoftLayer vlans associated with your account that are usable for assigning to
|
16
|
+
CCI's during `vagrant-softlayer` provisioning. It provides the id, name, and qualified
|
17
|
+
name of vlans that can be used with the `vlan_private` and `vlan_public`
|
18
|
+
`vagrant-softlayer` settings.
|
@@ -1,408 +1,416 @@
|
|
1
|
-
#!/usr/bin/env ruby
|
2
|
-
|
3
|
-
require 'getoptlong'
|
4
|
-
require 'tmpdir'
|
5
|
-
|
6
|
-
require 'rubygems'
|
7
|
-
require 'softlayer_api'
|
8
|
-
|
9
|
-
$sl = {
|
10
|
-
:data => {
|
11
|
-
:create_opts => nil,
|
12
|
-
:private_images => nil,
|
13
|
-
:public_images => nil
|
14
|
-
},
|
15
|
-
:service => {
|
16
|
-
:account => nil,
|
17
|
-
:virtual_guest => nil,
|
18
|
-
:virtual_guest_block_device_template_group => nil
|
19
|
-
},
|
20
|
-
:sl_credentials => {
|
21
|
-
:api_key => nil,
|
22
|
-
:endpoint_url => SoftLayer::API_PUBLIC_ENDPOINT,
|
23
|
-
:username => nil
|
24
|
-
}
|
25
|
-
}
|
26
|
-
|
27
|
-
$boxes = {
|
28
|
-
:data => {},
|
29
|
-
:datacenter => nil,
|
30
|
-
:dir => {
|
31
|
-
:boxes => "boxes",
|
32
|
-
:vagrantfiles => "vagrantfiles",
|
33
|
-
:boxes_root => nil,
|
34
|
-
:output_root => File.expand_path("."),
|
35
|
-
:vagrantfiles_root => nil
|
36
|
-
},
|
37
|
-
:domain => nil,
|
38
|
-
:file_templates => {
|
39
|
-
:created_by => "# vagrant-softlayer-boxes automatic template export",
|
40
|
-
:end => "end",
|
41
|
-
:image_detail => "# Compute or flex image details:",
|
42
|
-
:indent => Hash.new() { |hash, key| hash[key] = " " * key },
|
43
|
-
:metadata_json => "{\"provider\": \"softlayer\"}",
|
44
|
-
:os_templates_avail => "# Available versions of this OS template (based on VM property selections):",
|
45
|
-
:sl_config_start => "config.vm.provider :softlayer do |sl|",
|
46
|
-
:vagrant_config_start => "Vagrant.configure(\"2\") do |config|"
|
47
|
-
},
|
48
|
-
:filter => nil,
|
49
|
-
:images => {
|
50
|
-
:private => true,
|
51
|
-
:public => true
|
52
|
-
},
|
53
|
-
:metadata_path => nil,
|
54
|
-
:monthly_billing => nil,
|
55
|
-
:templates => true,
|
56
|
-
:vlan_private => nil,
|
57
|
-
:vlan_public => nil
|
58
|
-
}
|
59
|
-
|
60
|
-
def procCliOptions()
|
61
|
-
opts = GetoptLong.new(
|
62
|
-
[ '--help', '-h', GetoptLong::NO_ARGUMENT ],
|
63
|
-
[ '--output_dir', '-o', GetoptLong::REQUIRED_ARGUMENT ],
|
64
|
-
[ '--only_images', '-i', GetoptLong::NO_ARGUMENT ],
|
65
|
-
[ '--only_private_images', '-p', GetoptLong::NO_ARGUMENT ],
|
66
|
-
[ '--only_public_images', '-g', GetoptLong::NO_ARGUMENT ],
|
67
|
-
[ '--only_templates', '-t', GetoptLong::NO_ARGUMENT ],
|
68
|
-
[ '--default_domain', GetoptLong::REQUIRED_ARGUMENT ],
|
69
|
-
[ '--default_datacenter', GetoptLong::REQUIRED_ARGUMENT ],
|
70
|
-
[ '--default_monthly_billing', GetoptLong::NO_ARGUMENT ],
|
71
|
-
[ '--default_vlan_private', GetoptLong::REQUIRED_ARGUMENT ],
|
72
|
-
[ '--default_vlan_public', GetoptLong::REQUIRED_ARGUMENT ],
|
73
|
-
[ '--sl_api_key', '-k', GetoptLong::REQUIRED_ARGUMENT ],
|
74
|
-
[ '--sl_endpoint_url', '-e', GetoptLong::REQUIRED_ARGUMENT ],
|
75
|
-
[ '--sl_username','-u', GetoptLong::REQUIRED_ARGUMENT ]
|
76
|
-
)
|
77
|
-
|
78
|
-
opts.each do | opt, optval |
|
79
|
-
case opt
|
80
|
-
when '--help'
|
81
|
-
puts <<-EOF
|
82
|
-
vagrant-softlayer-boxes [OPTION] [FILTER]
|
83
|
-
|
84
|
-
--help, -h:
|
85
|
-
Print this help.
|
86
|
-
|
87
|
-
--sl_username USERNAME, -u USERNAME:
|
88
|
-
Sets the SoftLayer account user name. If not specified, it is assumed SL_API_USERNAME environment variable is set.
|
89
|
-
|
90
|
-
--sl_api_key SL_API_KEY, -k SL_API_KEY:
|
91
|
-
Sets the SoftLayer API key. If not specified, it is assumed SL_API_KEY environment variable is set.
|
92
|
-
|
93
|
-
--sl_endpoint_url SL_API_BASE_URL, -e SL_API_BASE_URL:
|
94
|
-
Sets the SoftLayer endpoint URL. If not specified, it assumed SL_API_BASE_URL environment variable is set to API_PUBLIC_ENDPOINT or API_PRIVATE_ENDPOINT.
|
95
|
-
Defaults to API_PUBLIC_ENDPOINT.
|
96
|
-
|
97
|
-
--output_dir OUTPUTDIR, -o OUTPUTDIR:
|
98
|
-
Sets the root directory to create box output under.
|
99
|
-
|
100
|
-
--only_templates, -t:
|
101
|
-
Only create boxes for the CCI templates and not compute or flex images.
|
102
|
-
|
103
|
-
--only_images, -i:
|
104
|
-
Only create boxes for the compute or flex images and not the CCI templates.
|
105
|
-
|
106
|
-
--only_public_images, -g:
|
107
|
-
Only create boxes for the public compute or flex images and not the CCI templates.
|
108
|
-
|
109
|
-
--only_private_images, -p:
|
110
|
-
Only create boxes for the private compute or flex images and not the CCI templates.
|
111
|
-
|
112
|
-
--default_domain:
|
113
|
-
Set default vm domain.
|
114
|
-
|
115
|
-
--default_datacenter:
|
116
|
-
Set default vm datacenter.
|
117
|
-
|
118
|
-
--default_monthly_billing:
|
119
|
-
Set default billing type to monthly.
|
120
|
-
|
121
|
-
--default_vlan_private:
|
122
|
-
Set default vm private vlan.
|
123
|
-
|
124
|
-
--default_vlan_public:
|
125
|
-
Set default vm public vlan.
|
126
|
-
|
127
|
-
FILTER
|
128
|
-
String used to filter template and compute/flex images by name to export boxes for specific matches. Supports filtering by regular expression.
|
129
|
-
|
130
|
-
EOF
|
131
|
-
|
132
|
-
exit 0
|
133
|
-
|
134
|
-
when '--sl_username'
|
135
|
-
$sl[:sl_credentials][:username] = optval.to_s
|
136
|
-
|
137
|
-
when '--sl_api_key'
|
138
|
-
$sl[:sl_credentials][:api_key] = optval.to_s
|
139
|
-
|
140
|
-
when '--sl_endpoint_url'
|
141
|
-
if ! [ "API_PUBLIC_ENDPOINT", "API_PRIVATE_ENDPOINT" ].include?(optval.to_s.upcase)
|
142
|
-
$stderr.puts "ERROR: Invalid endpoint_url value: " + optval.to_s.upcase
|
143
|
-
exit 2
|
144
|
-
end
|
145
|
-
|
146
|
-
$sl[:sl_credentials][:endpoint_url] = (optval.to_s.upcase == 'API_PUBLIC_ENDPOINT' ? SoftLayer::API_PUBLIC_ENDPOINT : SoftLayer::API_PRIVATE_ENDPOINT )
|
147
|
-
|
148
|
-
when '--output_dir'
|
149
|
-
if File.exists?(optval.to_s) && File.ftype(optval.to_s) != 'directory'
|
150
|
-
$stderr.puts "ERROR: Path is not a directory: " + optval.to_s
|
151
|
-
exit 2
|
152
|
-
end
|
153
|
-
|
154
|
-
$boxes[:dir][:output_root] = File.expand_path(optval.to_s)
|
155
|
-
$boxes[:dir][:vagrantfiles_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles])
|
156
|
-
$boxes[:dir][:boxes_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:boxes])
|
157
|
-
|
158
|
-
if File.exists?($boxes[:dir][:vagrantfiles_root]) && File.ftype($boxes[:dir][:vagrantfiles_root]) != 'directory'
|
159
|
-
$stderr.puts "ERROR: Output directory subdir is not a directory: " + $boxes[:dir][:vagrantfiles_root]
|
160
|
-
exit 2
|
161
|
-
end
|
162
|
-
|
163
|
-
if File.exists?($boxes[:dir][:boxes_root]) && File.ftype($boxes[:dir][:boxes_root]) != 'directory'
|
164
|
-
$stderr.puts "ERROR: Output directory subdir is not a directory: " + $boxes[:dir][:boxes_root]
|
165
|
-
exit 2
|
166
|
-
end
|
167
|
-
|
168
|
-
when '--only_templates'
|
169
|
-
$boxes[:images][:public] = false
|
170
|
-
$boxes[:images][:private] = false
|
171
|
-
|
172
|
-
when '--only_images'
|
173
|
-
$boxes[:templates] = false
|
174
|
-
|
175
|
-
when '--only_public_images'
|
176
|
-
$boxes[:templates] = false
|
177
|
-
$boxes[:images][:private] = false
|
178
|
-
|
179
|
-
when '--only_private_images'
|
180
|
-
$boxes[:templates] = false
|
181
|
-
$boxes[:images][:public] = false
|
182
|
-
|
183
|
-
when '--default_domain'
|
184
|
-
$boxes[:domain] = optval.to_s
|
185
|
-
|
186
|
-
when '--default_datacenter'
|
187
|
-
$boxes[:datacenter] = optval.to_s
|
188
|
-
|
189
|
-
when '--default_monthly_billing'
|
190
|
-
$boxes[:monthly_billing] = true
|
191
|
-
|
192
|
-
when '--default_vlan_private'
|
193
|
-
$boxes[:vlan_private] = optval.to_s
|
194
|
-
|
195
|
-
when'--default_vlan_public'
|
196
|
-
$boxes[:vlan_public] = optval.to_s
|
197
|
-
|
198
|
-
end
|
199
|
-
end
|
200
|
-
|
201
|
-
$boxes[:dir][:vagrantfiles_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles])
|
202
|
-
$boxes[:dir][:boxes_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:boxes])
|
203
|
-
$boxes[:metadata_path] = File.join($boxes[:dir][:output_root], "metadata.json")
|
204
|
-
|
205
|
-
begin
|
206
|
-
[ $boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles_root], $boxes[:dir][:boxes_root] ].each do |path|
|
207
|
-
Dir.mkdir(path, 0755) if ! File.exists?(path)
|
208
|
-
end
|
209
|
-
rescue Exception => e
|
210
|
-
$stderr.puts "ERROR: Failed to create output directories: " + e.message
|
211
|
-
exit 1
|
212
|
-
end
|
213
|
-
|
214
|
-
$sl[:sl_credentials][:username] = ENV["SL_API_USERNAME"] if $sl[:sl_credentials][:username].nil? && ENV.include?("SL_API_USERNAME")
|
215
|
-
$sl[:sl_credentials][:api_key] = ENV["SL_API_KEY"] if $sl[:sl_credentials][:api_key].nil? && ENV.include?("SL_API_KEY")
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
231
|
-
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
|
258
|
-
|
259
|
-
$sl[:
|
260
|
-
$sl[:
|
261
|
-
|
262
|
-
|
263
|
-
|
264
|
-
|
265
|
-
|
266
|
-
|
267
|
-
|
268
|
-
$sl[:data][:
|
269
|
-
|
270
|
-
|
271
|
-
|
272
|
-
|
273
|
-
|
274
|
-
|
275
|
-
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
$boxes[:data][boxgroup]
|
284
|
-
|
285
|
-
|
286
|
-
|
287
|
-
|
288
|
-
|
289
|
-
|
290
|
-
|
291
|
-
boxgroup
|
292
|
-
|
293
|
-
|
294
|
-
|
295
|
-
|
296
|
-
|
297
|
-
|
298
|
-
|
299
|
-
|
300
|
-
|
301
|
-
|
302
|
-
|
303
|
-
|
304
|
-
|
305
|
-
|
306
|
-
|
307
|
-
|
308
|
-
|
309
|
-
|
310
|
-
|
311
|
-
|
312
|
-
|
313
|
-
|
314
|
-
|
315
|
-
|
316
|
-
|
317
|
-
|
318
|
-
|
319
|
-
|
320
|
-
|
321
|
-
|
322
|
-
|
323
|
-
|
324
|
-
|
325
|
-
|
326
|
-
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
334
|
-
|
335
|
-
|
336
|
-
|
337
|
-
|
338
|
-
|
339
|
-
|
340
|
-
|
341
|
-
|
342
|
-
|
343
|
-
|
344
|
-
fout.puts
|
345
|
-
fout.puts
|
346
|
-
|
347
|
-
fout.puts
|
348
|
-
|
349
|
-
|
350
|
-
fout.puts $boxes[:file_templates][:
|
351
|
-
fout.puts
|
352
|
-
|
353
|
-
fout.puts
|
354
|
-
fout.puts
|
355
|
-
fout.puts
|
356
|
-
|
357
|
-
fout.puts
|
358
|
-
fout.puts $boxes[:file_templates][:
|
359
|
-
fout.puts $boxes[:file_templates][:indent][
|
360
|
-
|
361
|
-
fout.puts $boxes[:file_templates][:indent][
|
362
|
-
fout.puts $boxes[:file_templates][:
|
363
|
-
|
364
|
-
|
365
|
-
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
end
|
371
|
-
|
372
|
-
|
373
|
-
|
374
|
-
|
375
|
-
|
376
|
-
|
377
|
-
|
378
|
-
|
379
|
-
|
380
|
-
|
381
|
-
|
382
|
-
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
FileUtils.
|
389
|
-
|
390
|
-
|
391
|
-
|
392
|
-
|
393
|
-
|
394
|
-
|
395
|
-
|
396
|
-
|
397
|
-
end
|
398
|
-
|
399
|
-
|
400
|
-
|
401
|
-
|
402
|
-
|
403
|
-
|
404
|
-
|
405
|
-
|
406
|
-
|
407
|
-
|
408
|
-
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require 'getoptlong'
|
4
|
+
require 'tmpdir'
|
5
|
+
|
6
|
+
require 'rubygems'
|
7
|
+
require 'softlayer_api'
|
8
|
+
|
9
|
+
$sl = {
|
10
|
+
:data => {
|
11
|
+
:create_opts => nil,
|
12
|
+
:private_images => nil,
|
13
|
+
:public_images => nil
|
14
|
+
},
|
15
|
+
:service => {
|
16
|
+
:account => nil,
|
17
|
+
:virtual_guest => nil,
|
18
|
+
:virtual_guest_block_device_template_group => nil
|
19
|
+
},
|
20
|
+
:sl_credentials => {
|
21
|
+
:api_key => nil,
|
22
|
+
:endpoint_url => SoftLayer::API_PUBLIC_ENDPOINT,
|
23
|
+
:username => nil
|
24
|
+
}
|
25
|
+
}
|
26
|
+
|
27
|
+
$boxes = {
|
28
|
+
:data => {},
|
29
|
+
:datacenter => nil,
|
30
|
+
:dir => {
|
31
|
+
:boxes => "boxes",
|
32
|
+
:vagrantfiles => "vagrantfiles",
|
33
|
+
:boxes_root => nil,
|
34
|
+
:output_root => File.expand_path("."),
|
35
|
+
:vagrantfiles_root => nil
|
36
|
+
},
|
37
|
+
:domain => nil,
|
38
|
+
:file_templates => {
|
39
|
+
:created_by => "# vagrant-softlayer-boxes automatic template export",
|
40
|
+
:end => "end",
|
41
|
+
:image_detail => "# Compute or flex image details:",
|
42
|
+
:indent => Hash.new() { |hash, key| hash[key] = " " * key },
|
43
|
+
:metadata_json => "{\"provider\": \"softlayer\"}",
|
44
|
+
:os_templates_avail => "# Available versions of this OS template (based on VM property selections):",
|
45
|
+
:sl_config_start => "config.vm.provider :softlayer do |sl|",
|
46
|
+
:vagrant_config_start => "Vagrant.configure(\"2\") do |config|"
|
47
|
+
},
|
48
|
+
:filter => nil,
|
49
|
+
:images => {
|
50
|
+
:private => true,
|
51
|
+
:public => true
|
52
|
+
},
|
53
|
+
:metadata_path => nil,
|
54
|
+
:monthly_billing => nil,
|
55
|
+
:templates => true,
|
56
|
+
:vlan_private => nil,
|
57
|
+
:vlan_public => nil
|
58
|
+
}
|
59
|
+
|
60
|
+
def procCliOptions()
|
61
|
+
opts = GetoptLong.new(
|
62
|
+
[ '--help', '-h', GetoptLong::NO_ARGUMENT ],
|
63
|
+
[ '--output_dir', '-o', GetoptLong::REQUIRED_ARGUMENT ],
|
64
|
+
[ '--only_images', '-i', GetoptLong::NO_ARGUMENT ],
|
65
|
+
[ '--only_private_images', '-p', GetoptLong::NO_ARGUMENT ],
|
66
|
+
[ '--only_public_images', '-g', GetoptLong::NO_ARGUMENT ],
|
67
|
+
[ '--only_templates', '-t', GetoptLong::NO_ARGUMENT ],
|
68
|
+
[ '--default_domain', GetoptLong::REQUIRED_ARGUMENT ],
|
69
|
+
[ '--default_datacenter', GetoptLong::REQUIRED_ARGUMENT ],
|
70
|
+
[ '--default_monthly_billing', GetoptLong::NO_ARGUMENT ],
|
71
|
+
[ '--default_vlan_private', GetoptLong::REQUIRED_ARGUMENT ],
|
72
|
+
[ '--default_vlan_public', GetoptLong::REQUIRED_ARGUMENT ],
|
73
|
+
[ '--sl_api_key', '-k', GetoptLong::REQUIRED_ARGUMENT ],
|
74
|
+
[ '--sl_endpoint_url', '-e', GetoptLong::REQUIRED_ARGUMENT ],
|
75
|
+
[ '--sl_username','-u', GetoptLong::REQUIRED_ARGUMENT ]
|
76
|
+
)
|
77
|
+
|
78
|
+
opts.each do | opt, optval |
|
79
|
+
case opt
|
80
|
+
when '--help'
|
81
|
+
puts <<-EOF
|
82
|
+
vagrant-softlayer-boxes [OPTION] [FILTER]
|
83
|
+
|
84
|
+
--help, -h:
|
85
|
+
Print this help.
|
86
|
+
|
87
|
+
--sl_username USERNAME, -u USERNAME:
|
88
|
+
Sets the SoftLayer account user name. If not specified, it is assumed SL_API_USERNAME environment variable is set.
|
89
|
+
|
90
|
+
--sl_api_key SL_API_KEY, -k SL_API_KEY:
|
91
|
+
Sets the SoftLayer API key. If not specified, it is assumed SL_API_KEY environment variable is set.
|
92
|
+
|
93
|
+
--sl_endpoint_url SL_API_BASE_URL, -e SL_API_BASE_URL:
|
94
|
+
Sets the SoftLayer endpoint URL. If not specified, it assumed SL_API_BASE_URL environment variable is set to API_PUBLIC_ENDPOINT or API_PRIVATE_ENDPOINT.
|
95
|
+
Defaults to API_PUBLIC_ENDPOINT.
|
96
|
+
|
97
|
+
--output_dir OUTPUTDIR, -o OUTPUTDIR:
|
98
|
+
Sets the root directory to create box output under.
|
99
|
+
|
100
|
+
--only_templates, -t:
|
101
|
+
Only create boxes for the CCI templates and not compute or flex images.
|
102
|
+
|
103
|
+
--only_images, -i:
|
104
|
+
Only create boxes for the compute or flex images and not the CCI templates.
|
105
|
+
|
106
|
+
--only_public_images, -g:
|
107
|
+
Only create boxes for the public compute or flex images and not the CCI templates.
|
108
|
+
|
109
|
+
--only_private_images, -p:
|
110
|
+
Only create boxes for the private compute or flex images and not the CCI templates.
|
111
|
+
|
112
|
+
--default_domain:
|
113
|
+
Set default vm domain.
|
114
|
+
|
115
|
+
--default_datacenter:
|
116
|
+
Set default vm datacenter.
|
117
|
+
|
118
|
+
--default_monthly_billing:
|
119
|
+
Set default billing type to monthly.
|
120
|
+
|
121
|
+
--default_vlan_private:
|
122
|
+
Set default vm private vlan.
|
123
|
+
|
124
|
+
--default_vlan_public:
|
125
|
+
Set default vm public vlan.
|
126
|
+
|
127
|
+
FILTER
|
128
|
+
String used to filter template and compute/flex images by name to export boxes for specific matches. Supports filtering by regular expression.
|
129
|
+
|
130
|
+
EOF
|
131
|
+
|
132
|
+
exit 0
|
133
|
+
|
134
|
+
when '--sl_username'
|
135
|
+
$sl[:sl_credentials][:username] = optval.to_s
|
136
|
+
|
137
|
+
when '--sl_api_key'
|
138
|
+
$sl[:sl_credentials][:api_key] = optval.to_s
|
139
|
+
|
140
|
+
when '--sl_endpoint_url'
|
141
|
+
if ! [ "API_PUBLIC_ENDPOINT", "API_PRIVATE_ENDPOINT" ].include?(optval.to_s.upcase)
|
142
|
+
$stderr.puts "ERROR: Invalid endpoint_url value: " + optval.to_s.upcase
|
143
|
+
exit 2
|
144
|
+
end
|
145
|
+
|
146
|
+
$sl[:sl_credentials][:endpoint_url] = (optval.to_s.upcase == 'API_PUBLIC_ENDPOINT' ? SoftLayer::API_PUBLIC_ENDPOINT : SoftLayer::API_PRIVATE_ENDPOINT )
|
147
|
+
|
148
|
+
when '--output_dir'
|
149
|
+
if File.exists?(optval.to_s) && File.ftype(optval.to_s) != 'directory'
|
150
|
+
$stderr.puts "ERROR: Path is not a directory: " + optval.to_s
|
151
|
+
exit 2
|
152
|
+
end
|
153
|
+
|
154
|
+
$boxes[:dir][:output_root] = File.expand_path(optval.to_s)
|
155
|
+
$boxes[:dir][:vagrantfiles_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles])
|
156
|
+
$boxes[:dir][:boxes_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:boxes])
|
157
|
+
|
158
|
+
if File.exists?($boxes[:dir][:vagrantfiles_root]) && File.ftype($boxes[:dir][:vagrantfiles_root]) != 'directory'
|
159
|
+
$stderr.puts "ERROR: Output directory subdir is not a directory: " + $boxes[:dir][:vagrantfiles_root]
|
160
|
+
exit 2
|
161
|
+
end
|
162
|
+
|
163
|
+
if File.exists?($boxes[:dir][:boxes_root]) && File.ftype($boxes[:dir][:boxes_root]) != 'directory'
|
164
|
+
$stderr.puts "ERROR: Output directory subdir is not a directory: " + $boxes[:dir][:boxes_root]
|
165
|
+
exit 2
|
166
|
+
end
|
167
|
+
|
168
|
+
when '--only_templates'
|
169
|
+
$boxes[:images][:public] = false
|
170
|
+
$boxes[:images][:private] = false
|
171
|
+
|
172
|
+
when '--only_images'
|
173
|
+
$boxes[:templates] = false
|
174
|
+
|
175
|
+
when '--only_public_images'
|
176
|
+
$boxes[:templates] = false
|
177
|
+
$boxes[:images][:private] = false
|
178
|
+
|
179
|
+
when '--only_private_images'
|
180
|
+
$boxes[:templates] = false
|
181
|
+
$boxes[:images][:public] = false
|
182
|
+
|
183
|
+
when '--default_domain'
|
184
|
+
$boxes[:domain] = optval.to_s
|
185
|
+
|
186
|
+
when '--default_datacenter'
|
187
|
+
$boxes[:datacenter] = optval.to_s
|
188
|
+
|
189
|
+
when '--default_monthly_billing'
|
190
|
+
$boxes[:monthly_billing] = true
|
191
|
+
|
192
|
+
when '--default_vlan_private'
|
193
|
+
$boxes[:vlan_private] = optval.to_s
|
194
|
+
|
195
|
+
when'--default_vlan_public'
|
196
|
+
$boxes[:vlan_public] = optval.to_s
|
197
|
+
|
198
|
+
end
|
199
|
+
end
|
200
|
+
|
201
|
+
$boxes[:dir][:vagrantfiles_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles])
|
202
|
+
$boxes[:dir][:boxes_root] = File.join($boxes[:dir][:output_root], $boxes[:dir][:boxes])
|
203
|
+
$boxes[:metadata_path] = File.join($boxes[:dir][:output_root], "metadata.json")
|
204
|
+
|
205
|
+
begin
|
206
|
+
[ $boxes[:dir][:output_root], $boxes[:dir][:vagrantfiles_root], $boxes[:dir][:boxes_root] ].each do |path|
|
207
|
+
Dir.mkdir(path, 0755) if ! File.exists?(path)
|
208
|
+
end
|
209
|
+
rescue Exception => e
|
210
|
+
$stderr.puts "ERROR: Failed to create output directories: " + e.message
|
211
|
+
exit 1
|
212
|
+
end
|
213
|
+
|
214
|
+
$sl[:sl_credentials][:username] = ENV["SL_API_USERNAME"] if $sl[:sl_credentials][:username].nil? && ENV.include?("SL_API_USERNAME")
|
215
|
+
$sl[:sl_credentials][:api_key] = ENV["SL_API_KEY"] if $sl[:sl_credentials][:api_key].nil? && ENV.include?("SL_API_KEY")
|
216
|
+
|
217
|
+
if $sl[:sl_credentials][:endpoint_url].nil? && ENV.include?("SL_API_BASE_URL")
|
218
|
+
if ! [ 'API_PRIVATE_ENDPOINT', 'API_PUBLIC_ENDPOINT' ].include?(ENV["SL_API_BASE_URL"])
|
219
|
+
$stderr.puts "ERROR: Invalid SoftLayer endpoint URL specified in environment variable SL_API_BASE_URL, expected one of #{[ 'API_PRIVATE_ENDPOINT', 'API_PUBLIC_ENDPOINT' ].inspect}: #{ENV["SL_API_BASE_URL"].inspect}"
|
220
|
+
exit 2
|
221
|
+
end
|
222
|
+
|
223
|
+
$sl[:sl_credentials][:endpoint_url] = (ENV["SL_API_BASE_URL"] == "API_PUBLIC_ENDPOINT" ? SoftLayer::API_PUBLIC_ENDPOINT : SoftLayer::API_PRIVATE_ENDPOINT )
|
224
|
+
end
|
225
|
+
|
226
|
+
if $sl[:sl_credentials][:username].nil?
|
227
|
+
$stderr.puts "ERROR: No SoftLayer username specified"
|
228
|
+
exit 2
|
229
|
+
end
|
230
|
+
|
231
|
+
if $sl[:sl_credentials][:username].nil?
|
232
|
+
$stderr.puts "ERROR: No SoftLayer user name specified"
|
233
|
+
exit 2
|
234
|
+
end
|
235
|
+
|
236
|
+
if $sl[:sl_credentials][:api_key].nil?
|
237
|
+
$stderr.puts "ERROR: No SoftLayer API key specified"
|
238
|
+
exit 2
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
242
|
+
def procCliArgs()
|
243
|
+
if ARGV.length > 2
|
244
|
+
$stderr.puts "ERROR: Invalid argument supplied, please check help"
|
245
|
+
exit 2
|
246
|
+
elsif ARGV.length == 1
|
247
|
+
begin
|
248
|
+
$boxes[:filter] = Regexp.new(ARGV[0], Regexp::IGNORECASE)
|
249
|
+
rescue Exception => e
|
250
|
+
$stderr.puts "ERROR: Filter value is not a valid regular expression: " + e.message
|
251
|
+
exit 2
|
252
|
+
end
|
253
|
+
end
|
254
|
+
end
|
255
|
+
|
256
|
+
def getBoxData()
|
257
|
+
begin
|
258
|
+
$sl[:service][:virtual_guest] = SoftLayer::Service.new("SoftLayer_Virtual_Guest", $sl[:sl_credentials]) if $boxes[:templates]
|
259
|
+
$sl[:service][:account] = SoftLayer::Service.new("SoftLayer_Account", $sl[:sl_credentials]) if $boxes[:images][:private]
|
260
|
+
$sl[:service][:virtual_guest_block_device_template_group] = SoftLayer::Service.new("SoftLayer_Virtual_Guest_Block_Device_Template_Group", $sl[:sl_credentials]) if $boxes[:images][:public]
|
261
|
+
rescue Exception => e
|
262
|
+
$stderr.puts "ERROR: Failed to create SoftLayer service object: " + e.message
|
263
|
+
exit 1
|
264
|
+
end
|
265
|
+
|
266
|
+
begin
|
267
|
+
$sl[:data][:create_opts] = $sl[:service][:virtual_guest].getCreateObjectOptions if $boxes[:templates]
|
268
|
+
$sl[:data][:private_images] = $sl[:service][:account].getBlockDeviceTemplateGroups.delete_if { |block_device| ! block_device.has_key?("globalIdentifier") } if $boxes[:images][:private]
|
269
|
+
$sl[:data][:public_images] = $sl[:service][:virtual_guest_block_device_template_group].getPublicImages.delete_if { |block_device| ! block_device.has_key?("globalIdentifier") } if $boxes[:images][:public]
|
270
|
+
rescue Exception => e
|
271
|
+
$stderr.puts "ERROR: Failed to retrieve SoftLayer service data: " + e.message
|
272
|
+
exit 1
|
273
|
+
end
|
274
|
+
|
275
|
+
if $boxes[:templates]
|
276
|
+
$sl[:data][:create_opts]["operatingSystems"].each do |os|
|
277
|
+
boxgroup = os["template"]["operatingSystemReferenceCode"].strip.gsub(/[()]/,'').gsub(/[^a-zA-Z0-9_.-]/, '_').upcase
|
278
|
+
|
279
|
+
#We dont want to allow separate instances for templates of same group name since the only difference is additional descriptions
|
280
|
+
if ! $boxes[:data].has_key?(boxgroup)
|
281
|
+
$boxes[:data][boxgroup] = Array.new()
|
282
|
+
|
283
|
+
$boxes[:data][boxgroup].push(
|
284
|
+
{
|
285
|
+
:type => :template,
|
286
|
+
:name => os["template"]["operatingSystemReferenceCode"],
|
287
|
+
:description => [ os["itemPrice"]["item"]["description"] ]
|
288
|
+
}
|
289
|
+
)
|
290
|
+
else
|
291
|
+
$boxes[:data][boxgroup][0][:description].push(os["itemPrice"]["item"]["description"])
|
292
|
+
end
|
293
|
+
end
|
294
|
+
end
|
295
|
+
|
296
|
+
$boxes[:images].each_key do |image_view|
|
297
|
+
if $boxes[:images][image_view]
|
298
|
+
$sl[:data][(image_view == :public ? :public_images : :private_images)].each do |image|
|
299
|
+
boxgroup = image["name"].strip.gsub(/[()]/,'').gsub(/[^a-zA-Z0-9_.-]/, '_').upcase
|
300
|
+
|
301
|
+
$boxes[:data][boxgroup] = Array.new() if ! $boxes[:data].has_key?(boxgroup)
|
302
|
+
$boxes[:data][boxgroup].push(
|
303
|
+
{
|
304
|
+
:type => :block_image,
|
305
|
+
:name => image["name"],
|
306
|
+
:global_id => image["globalIdentifier"],
|
307
|
+
:note => image["note"].to_s,
|
308
|
+
:summary => image["summary"].to_s,
|
309
|
+
:visibility => image_view
|
310
|
+
}
|
311
|
+
)
|
312
|
+
end
|
313
|
+
end
|
314
|
+
end
|
315
|
+
end
|
316
|
+
|
317
|
+
def filterBoxes()
|
318
|
+
if ! $boxes[:filter].nil?
|
319
|
+
$boxes[:data].each_key do |boxgroup|
|
320
|
+
begin
|
321
|
+
$boxes[:data][boxgroup].delete_if { |box| ! box[:name].match($boxes[:filter]) }
|
322
|
+
rescue Exception => e
|
323
|
+
$stderr.puts "ERROR: Failed to filter Softlayer boxes: " + e.message
|
324
|
+
exit 1
|
325
|
+
end
|
326
|
+
end
|
327
|
+
end
|
328
|
+
end
|
329
|
+
|
330
|
+
def saveBoxFiles()
|
331
|
+
begin
|
332
|
+
File.open($boxes[:metadata_path], "w", 0644) { |fout| fout.puts $boxes[:file_templates][:metadata_json] }
|
333
|
+
rescue Exception => e
|
334
|
+
$stderr.puts "ERROR: Failed to save box metadata JSON data: " + e.message
|
335
|
+
exit 1
|
336
|
+
end
|
337
|
+
|
338
|
+
$boxes[:data].each_key do |boxgroup|
|
339
|
+
$boxes[:data][boxgroup].each do |box|
|
340
|
+
boxFileName = ($boxes[:data][boxgroup].length > 1 ? boxgroup + "_" + ($boxes[:data][boxgroup].index(box) + 1).to_s : boxgroup)
|
341
|
+
|
342
|
+
begin
|
343
|
+
File.open(File.join($boxes[:dir][:vagrantfiles_root], boxFileName + ".vagrantfile"), "w", 0644) do |fout|
|
344
|
+
fout.puts $boxes[:file_templates][:created_by]
|
345
|
+
fout.puts
|
346
|
+
|
347
|
+
fout.puts $boxes[:file_templates][:os_templates_avail] if box[:type] == :template
|
348
|
+
fout.puts box[:description].map { |descr| "# " + descr }.join("\n") if box[:type] == :template
|
349
|
+
|
350
|
+
fout.puts $boxes[:file_templates][:image_detail] if box[:type] == :block_image
|
351
|
+
fout.puts "# Global Identifier: " + box[:global_id].to_s if box[:type] == :block_image
|
352
|
+
fout.puts "# Name: " + box[:name] if box[:type] == :block_image
|
353
|
+
fout.puts "# Summary: " + box[:summary].to_s if box[:type] == :block_image
|
354
|
+
fout.puts "# Note: " + box[:note].to_s if box[:type] == :block_image
|
355
|
+
fout.puts "# Visibility: " + (box[:visibility] == :public ? "public" : "private" ) if box[:type] == :block_image
|
356
|
+
|
357
|
+
fout.puts
|
358
|
+
fout.puts $boxes[:file_templates][:vagrant_config_start]
|
359
|
+
fout.puts $boxes[:file_templates][:indent][4] + $boxes[:file_templates][:sl_config_start]
|
360
|
+
|
361
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.datacenter = \"" + $boxes[:datacenter] + "\"" if $boxes[:datacenter]
|
362
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.domain = \"" + $boxes[:domain] + "\"" if $boxes[:domain]
|
363
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.hourly_billing = false" if $boxes[:monthly_billing]
|
364
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.operating_system = \"" + box[:name] + "\"" if box[:type] == :template
|
365
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.image_guid = \"" + box[:global_id].to_s + "\"" if box[:type] == :block_image
|
366
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.vlan_private = \"" + $boxes[:vlan_private] + "\"" if $boxes[:vlan_private]
|
367
|
+
fout.puts $boxes[:file_templates][:indent][8] + "sl.vlan_public = \"" + $boxes[:vlan_public] + "\"" if $boxes[:vlan_public]
|
368
|
+
|
369
|
+
fout.puts $boxes[:file_templates][:indent][4] + $boxes[:file_templates][:end]
|
370
|
+
fout.puts $boxes[:file_templates][:end]
|
371
|
+
end
|
372
|
+
rescue Exception => e
|
373
|
+
$stderr.puts "ERROR: Failed to save box Vagrantfile: " + e.message
|
374
|
+
exit 1
|
375
|
+
end
|
376
|
+
end
|
377
|
+
end
|
378
|
+
end
|
379
|
+
|
380
|
+
def createBoxes()
|
381
|
+
$boxes[:data].each_key do |boxgroup|
|
382
|
+
$boxes[:data][boxgroup].each do |box|
|
383
|
+
boxFileName = ($boxes[:data][boxgroup].length > 1 ? boxgroup + "_" + ($boxes[:data][boxgroup].index(box) + 1).to_s : boxgroup)
|
384
|
+
|
385
|
+
begin
|
386
|
+
Dir.mktmpdir do |tmpDir|
|
387
|
+
FileUtils.cd(tmpDir) do
|
388
|
+
FileUtils.cp($boxes[:metadata_path], File.join(tmpDir,"metadata.json"), :preserve => true)
|
389
|
+
FileUtils.cp(File.join($boxes[:dir][:vagrantfiles_root], boxFileName + ".vagrantfile"), File.join(tmpDir, "Vagrantfile"), :preserve => true)
|
390
|
+
|
391
|
+
result = %x(tar -czvf "#{File.join($boxes[:dir][:boxes_root], boxFileName + ".box.tar.gz")}" Vagrantfile metadata.json)
|
392
|
+
|
393
|
+
raise result if $?.exitstatus != 0
|
394
|
+
|
395
|
+
FileUtils.mv(File.join($boxes[:dir][:boxes_root], boxFileName + ".box.tar.gz"), File.join($boxes[:dir][:boxes_root], boxFileName + ".box"), :force => true)
|
396
|
+
FileUtils.chmod(0644, File.join($boxes[:dir][:boxes_root], boxFileName + ".box"))
|
397
|
+
end
|
398
|
+
end
|
399
|
+
rescue Exception => e
|
400
|
+
$stderr.puts "ERROR: Failed to save Vagrant box: " + e.message
|
401
|
+
exit 1
|
402
|
+
end
|
403
|
+
end
|
404
|
+
end
|
405
|
+
end
|
406
|
+
|
407
|
+
def main()
|
408
|
+
procCliOptions()
|
409
|
+
procCliArgs()
|
410
|
+
getBoxData()
|
411
|
+
filterBoxes()
|
412
|
+
saveBoxFiles()
|
413
|
+
createBoxes()
|
414
|
+
end
|
415
|
+
|
416
|
+
main
|