knife-vcenter 1.0.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.
- checksums.yaml +7 -0
- data/.github/ISSUE_TEMPLATE.md +22 -0
- data/.github/PULL_REQUEST_TEMPLATE.md +14 -0
- data/.gitignore +20 -0
- data/.rubocop.yml +18 -0
- data/.travis.yml +16 -0
- data/CHANGELOG.md +12 -0
- data/Gemfile +3 -0
- data/LICENSE.txt +201 -0
- data/README.md +209 -0
- data/Rakefile +20 -0
- data/knife-vcenter.gemspec +38 -0
- data/lib/base.rb +35 -0
- data/lib/chef/knife/cloud/vcenter_service.rb +256 -0
- data/lib/chef/knife/cloud/vcenter_service_helpers.rb +55 -0
- data/lib/chef/knife/cloud/vcenter_service_options.rb +56 -0
- data/lib/chef/knife/vcenter_cluster_list.rb +58 -0
- data/lib/chef/knife/vcenter_datacenter_list.rb +51 -0
- data/lib/chef/knife/vcenter_host_list.rb +67 -0
- data/lib/chef/knife/vcenter_vm_clone.rb +100 -0
- data/lib/chef/knife/vcenter_vm_create.rb +82 -0
- data/lib/chef/knife/vcenter_vm_delete.rb +54 -0
- data/lib/chef/knife/vcenter_vm_list.rb +68 -0
- data/lib/chef/knife/vcenter_vm_show.rb +54 -0
- data/lib/knife-vcenter/version.rb +22 -0
- data/lib/lookup_service_helper.rb +463 -0
- data/lib/sso.rb +269 -0
- data/lib/support/clone_vm.rb +74 -0
- data/spec/spec_helper.rb +18 -0
- data/spec/unit/vcenter_vm_list_spec.rb +67 -0
- metadata +257 -0
data/lib/sso.rb
ADDED
@@ -0,0 +1,269 @@
|
|
1
|
+
# Copyright 2014-2017 VMware, Inc. All Rights Reserved.
|
2
|
+
# SPDX-License-Identifier: MIT
|
3
|
+
|
4
|
+
require 'savon'
|
5
|
+
require 'nokogiri'
|
6
|
+
require 'date'
|
7
|
+
require 'securerandom'
|
8
|
+
|
9
|
+
# A little utility library for VMware SSO.
|
10
|
+
# For now, this is not a general purpose library that covers all
|
11
|
+
# the interfaces of the SSO service.
|
12
|
+
# Specifically, the support is limited to the following:
|
13
|
+
# * request bearer token.
|
14
|
+
module SSO
|
15
|
+
|
16
|
+
# The XML date format.
|
17
|
+
DATE_FORMAT = "%FT%T.%LZ"
|
18
|
+
|
19
|
+
# The XML namespaces that are required: SOAP, WSDL, et al.
|
20
|
+
NAMESPACES = {
|
21
|
+
"xmlns:S" => "http://schemas.xmlsoap.org/soap/envelope/",
|
22
|
+
"xmlns:wst" => "http://docs.oasis-open.org/ws-sx/ws-trust/200512",
|
23
|
+
"xmlns:u" => "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd",
|
24
|
+
"xmlns:x" => "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd",
|
25
|
+
}
|
26
|
+
|
27
|
+
# Provides the connection details for the SSO service.
|
28
|
+
class Connection
|
29
|
+
|
30
|
+
attr_accessor :sso_url, :wsdl_url, :username, :password
|
31
|
+
|
32
|
+
# Creates a new instance.
|
33
|
+
def initialize(sso_url, wsdl_url=nil)
|
34
|
+
self.sso_url = sso_url
|
35
|
+
self.wsdl_url = wsdl_url || "#{sso_url}?wsdl"
|
36
|
+
end
|
37
|
+
|
38
|
+
# Login with the given credentials.
|
39
|
+
# Note: this does not invoke a login action, but rather stores the
|
40
|
+
# credentials for use later.
|
41
|
+
def login(username, password)
|
42
|
+
self.username = username
|
43
|
+
self.password = password
|
44
|
+
self # enable builder pattern
|
45
|
+
end
|
46
|
+
|
47
|
+
# Gets (or creates) the Savon client instance.
|
48
|
+
def client
|
49
|
+
# construct and init the client proxy
|
50
|
+
@client ||= Savon.client do |globals|
|
51
|
+
# see: http://savonrb.com/version2/globals.html
|
52
|
+
globals.wsdl wsdl_url
|
53
|
+
globals.endpoint sso_url
|
54
|
+
|
55
|
+
globals.strip_namespaces false
|
56
|
+
globals.env_namespace :S
|
57
|
+
|
58
|
+
# set like this so https connection does not fail
|
59
|
+
# TODO: find an acceptable solution for production
|
60
|
+
globals.ssl_verify_mode :none
|
61
|
+
|
62
|
+
# dev/debug settings
|
63
|
+
# globals.pretty_print_xml ENV['DEBUG_SOAP']
|
64
|
+
# globals.log ENV['DEBUG_SOAP']
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
# Invokes the request bearer token operation.
|
69
|
+
# @return [SamlToken]
|
70
|
+
def request_bearer_token()
|
71
|
+
rst = RequestSecurityToken.new(client, username, password)
|
72
|
+
rst.invoke()
|
73
|
+
rst.saml_token
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
# @abstract Base class for invocable service calls.
|
78
|
+
class SoapInvocable
|
79
|
+
|
80
|
+
attr_reader :operation, :client, :response
|
81
|
+
|
82
|
+
# Constructs a new instance.
|
83
|
+
# @param operation [Symbol] the SOAP operation name (in Symbol form)
|
84
|
+
# @param client [Savon::Client] the client
|
85
|
+
def initialize(operation, client)
|
86
|
+
@operation = operation
|
87
|
+
@client = client
|
88
|
+
end
|
89
|
+
|
90
|
+
# Invokes the service call represented by this type.
|
91
|
+
def invoke
|
92
|
+
request = request_xml.to_s
|
93
|
+
puts "request = #{request}" if ENV['DEBUG']
|
94
|
+
@response = client.call(operation, xml:request)
|
95
|
+
puts "response = #{response}" if ENV['DEBUG']
|
96
|
+
self # for chaining with new
|
97
|
+
end
|
98
|
+
|
99
|
+
# Builds the request XML content.
|
100
|
+
def request_xml
|
101
|
+
builder = Builder::XmlMarkup.new()
|
102
|
+
builder.instruct!(:xml, encoding: "UTF-8")
|
103
|
+
|
104
|
+
builder.tag!("S:Envelope", NAMESPACES) do |envelope|
|
105
|
+
if has_header?
|
106
|
+
envelope.tag!("S:Header") do |header|
|
107
|
+
header_xml(header)
|
108
|
+
end
|
109
|
+
end
|
110
|
+
envelope.tag!("S:Body") do |body|
|
111
|
+
body_xml(body)
|
112
|
+
end
|
113
|
+
end
|
114
|
+
builder.target!
|
115
|
+
end
|
116
|
+
|
117
|
+
def has_header?
|
118
|
+
true
|
119
|
+
end
|
120
|
+
|
121
|
+
# Builds the header portion of the SOAP request.
|
122
|
+
# Specific service operations must override this method.
|
123
|
+
def header_xml(header)
|
124
|
+
raise 'abstract method not implemented!'
|
125
|
+
end
|
126
|
+
|
127
|
+
# Builds the body portion of the SOAP request.
|
128
|
+
# Specific service operations must override this method.
|
129
|
+
def body_xml(body)
|
130
|
+
raise 'abstract method not implemented!'
|
131
|
+
end
|
132
|
+
|
133
|
+
# Gets the response XML content.
|
134
|
+
def response_xml
|
135
|
+
raise 'illegal state: response not set yet' if response.nil?
|
136
|
+
@response_xml ||= Nokogiri::XML(response.to_xml)
|
137
|
+
end
|
138
|
+
|
139
|
+
def response_hash
|
140
|
+
@response_hash ||= response.to_hash
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
# Encapsulates an issue operation that requests a security token
|
145
|
+
# from the SSO service.
|
146
|
+
class RequestSecurityToken < SoapInvocable
|
147
|
+
|
148
|
+
attr_accessor :request_type, :delegatable
|
149
|
+
|
150
|
+
# Constructs a new instance.
|
151
|
+
def initialize(client, username, password, hours=2)
|
152
|
+
super(:issue, client)
|
153
|
+
|
154
|
+
@username = username
|
155
|
+
@password = password
|
156
|
+
@hours = hours
|
157
|
+
|
158
|
+
#TODO: these things should be configurable, so we can get
|
159
|
+
#non-delegatable tokens, HoK tokens, etc.
|
160
|
+
@request_type = "http://docs.oasis-open.org/ws-sx/ws-trust/200512/Issue"
|
161
|
+
@delegatable = true
|
162
|
+
end
|
163
|
+
|
164
|
+
def now
|
165
|
+
@now ||= Time.now.utc.to_datetime
|
166
|
+
end
|
167
|
+
|
168
|
+
def created
|
169
|
+
@created ||= now.strftime(DATE_FORMAT)
|
170
|
+
end
|
171
|
+
|
172
|
+
def future
|
173
|
+
@future ||= now + (2/24.0) #days (for DateTime math)
|
174
|
+
end
|
175
|
+
|
176
|
+
def expires
|
177
|
+
@expires ||= future.strftime(DATE_FORMAT)
|
178
|
+
end
|
179
|
+
|
180
|
+
# Builds the header XML for the SOAP request.
|
181
|
+
def header_xml(header)
|
182
|
+
id = "uuid-" + SecureRandom.uuid
|
183
|
+
|
184
|
+
#header.tag!("x:Security", "x:mustUnderstand" => "1") do |security|
|
185
|
+
header.tag!("x:Security") do |security|
|
186
|
+
security.tag!("u:Timestamp", "u:Id" => "_0") do |timestamp|
|
187
|
+
timestamp.tag!("u:Created") do |element|
|
188
|
+
element << created
|
189
|
+
end
|
190
|
+
timestamp.tag!("u:Expires") do |element|
|
191
|
+
element << expires
|
192
|
+
end
|
193
|
+
end
|
194
|
+
security.tag!("x:UsernameToken", "u:Id" => id) do |utoken|
|
195
|
+
utoken.tag!("x:Username") do |element|
|
196
|
+
element << @username
|
197
|
+
end
|
198
|
+
utoken.tag!("x:Password") do |element|
|
199
|
+
element << @password
|
200
|
+
end
|
201
|
+
end
|
202
|
+
end
|
203
|
+
end
|
204
|
+
|
205
|
+
# Builds the body XML for the SOAP request.
|
206
|
+
def body_xml(body)
|
207
|
+
body.tag!("wst:RequestSecurityToken") do |rst|
|
208
|
+
rst.tag!("wst:RequestType") do |element|
|
209
|
+
element << request_type
|
210
|
+
end
|
211
|
+
rst.tag!("wst:Delegatable") do |element|
|
212
|
+
element << delegatable.to_s
|
213
|
+
end
|
214
|
+
=begin
|
215
|
+
#TODO: we don't seem to need this, but I'm leaving this
|
216
|
+
#here for now as a reminder.
|
217
|
+
rst.tag!("wst:Lifetime") do |lifetime|
|
218
|
+
lifetime.tag!("u:Created") do |element|
|
219
|
+
element << created
|
220
|
+
end
|
221
|
+
lifetime.tag!("u:Expires") do |element|
|
222
|
+
element << expires
|
223
|
+
end
|
224
|
+
end
|
225
|
+
=end
|
226
|
+
end
|
227
|
+
end
|
228
|
+
|
229
|
+
# Gets the saml_token from the SOAP response body.
|
230
|
+
# @return [SamlToken] the requested SAML token
|
231
|
+
def saml_token
|
232
|
+
assertion = response_xml.at_xpath('//saml2:Assertion',
|
233
|
+
'saml2' => 'urn:oasis:names:tc:SAML:2.0:assertion')
|
234
|
+
SamlToken.new(assertion)
|
235
|
+
end
|
236
|
+
end
|
237
|
+
|
238
|
+
# Holds a SAML token.
|
239
|
+
class SamlToken
|
240
|
+
attr_reader :xml
|
241
|
+
|
242
|
+
# Creates a new instance.
|
243
|
+
def initialize(xml)
|
244
|
+
@xml = xml
|
245
|
+
end
|
246
|
+
|
247
|
+
#TODO: add some getters for interesting content
|
248
|
+
|
249
|
+
def to_s
|
250
|
+
esc_token = xml.to_xml(:indent => 0, :encoding => 'UTF-8')
|
251
|
+
esc_token = esc_token.gsub(/\n/, '')
|
252
|
+
esc_token
|
253
|
+
end
|
254
|
+
end
|
255
|
+
end
|
256
|
+
|
257
|
+
# main: quick self tester
|
258
|
+
if __FILE__ == $0
|
259
|
+
cloudvm_ip = ARGV[0]
|
260
|
+
cloudvm_ip ||= "10.20.17.0"
|
261
|
+
#cloudvm_ip ||= "10.67.245.207"
|
262
|
+
sso_url = "https://#{cloudvm_ip}/sts/STSService/vsphere.local"
|
263
|
+
wsdl_url = "#{sso_url}?wsdl"
|
264
|
+
sso = SSO::Connection.new(sso_url, wsdl_url)
|
265
|
+
#sso.login("administrator@vsphere.local", "Admin!23")
|
266
|
+
sso.login("root", "vmware")
|
267
|
+
token = sso.request_bearer_token
|
268
|
+
puts token.to_s
|
269
|
+
end
|
@@ -0,0 +1,74 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
#
|
3
|
+
# Author:: Chef Partner Engineering (<partnereng@chef.io>)
|
4
|
+
# Copyright:: Copyright (c) 2017 Chef Software, Inc.
|
5
|
+
# License:: Apache License, Version 2.0
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
#
|
19
|
+
|
20
|
+
require 'rbvmomi'
|
21
|
+
|
22
|
+
class Support
|
23
|
+
class CloneVm
|
24
|
+
attr_reader :vim, :options
|
25
|
+
|
26
|
+
def initialize(conn_opts, options)
|
27
|
+
@options = options
|
28
|
+
|
29
|
+
# Connect to vSphere
|
30
|
+
@vim ||= RbVmomi::VIM.connect conn_opts
|
31
|
+
end
|
32
|
+
|
33
|
+
def clone
|
34
|
+
|
35
|
+
# set the datacenter name
|
36
|
+
dc = vim.serviceInstance.find_datacenter(options[:datacenter])
|
37
|
+
src_vm = dc.find_vm(options[:template])
|
38
|
+
hosts = dc.hostFolder.children
|
39
|
+
|
40
|
+
# Specify where the machine is going to be created
|
41
|
+
relocate_spec = RbVmomi::VIM.VirtualMachineRelocateSpec
|
42
|
+
relocate_spec.host = options[:targethost]
|
43
|
+
relocate_spec.pool = hosts.first.resourcePool
|
44
|
+
|
45
|
+
clone_spec = RbVmomi::VIM.VirtualMachineCloneSpec(location: relocate_spec,
|
46
|
+
powerOn: options[:poweron],
|
47
|
+
template: false)
|
48
|
+
|
49
|
+
# Set the folder to use
|
50
|
+
dest_folder = options[:folder].nil? ? src_vm.parent : options[:folder][:id]
|
51
|
+
|
52
|
+
puts "Cloning the template to create the new machine..."
|
53
|
+
task = src_vm.CloneVM_Task(folder: dest_folder, name: options[:name], spec: clone_spec)
|
54
|
+
# TODO: it would be nice to have dots to tell you it's working here
|
55
|
+
task.wait_for_completion
|
56
|
+
|
57
|
+
|
58
|
+
# get the IP address of the machine for bootstrapping
|
59
|
+
# machine name is based on the path, e.g. that includes the folder
|
60
|
+
name = options[:folder].nil? ? options[:name] : format("%s/%s", options[:folder][:name], options[:name])
|
61
|
+
new_vm = dc.find_vm(name)
|
62
|
+
|
63
|
+
if new_vm.nil?
|
64
|
+
puts format("Unable to find machine: %s", name)
|
65
|
+
else
|
66
|
+
puts 'Waiting for network interfaces to become available...'
|
67
|
+
sleep 2 while new_vm.guest.net.empty? || !new_vm.guest.ipAddress
|
68
|
+
new_vm.guest.net[0].ipConfig.ipAddress.detect do |addr|
|
69
|
+
addr.origin != 'linklayer'
|
70
|
+
end.ipAddress
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
#
|
3
|
+
# Author:: Chef Partner Engineering (<partnereng@chef.io>)
|
4
|
+
# Copyright:: Copyright (c) 2017 Chef Software, Inc.
|
5
|
+
# License:: Apache License, Version 2.0
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
#
|
@@ -0,0 +1,67 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
#
|
3
|
+
# Author:: Chef Partner Engineering (<partnereng@chef.io>)
|
4
|
+
# Copyright:: Copyright (c) 2017 Chef Software, Inc.
|
5
|
+
# License:: Apache License, Version 2.0
|
6
|
+
#
|
7
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
8
|
+
# you may not use this file except in compliance with the License.
|
9
|
+
# You may obtain a copy of the License at
|
10
|
+
#
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
12
|
+
#
|
13
|
+
# Unless required by applicable law or agreed to in writing, software
|
14
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
15
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
16
|
+
# See the License for the specific language governing permissions and
|
17
|
+
# limitations under the License.
|
18
|
+
#
|
19
|
+
|
20
|
+
require 'spec_helper'
|
21
|
+
require 'chef/knife/vcenter_vm_list'
|
22
|
+
require 'support/shared_examples_for_command'
|
23
|
+
|
24
|
+
class PowerStatus < BasicObject
|
25
|
+
attr_reader :value
|
26
|
+
def initialize(state)
|
27
|
+
@value = state
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
describe Chef::Knife::Cloud::VcenterVmList do
|
32
|
+
it_behaves_like Chef::Knife::Cloud::Command, Chef::Knife::Cloud::VcenterVmList.new
|
33
|
+
|
34
|
+
subject { described_class.new }
|
35
|
+
|
36
|
+
describe '#format_power_status' do
|
37
|
+
context 'when the power is "POWERED_ON"' do
|
38
|
+
it 'displays with green' do
|
39
|
+
expect(subject.ui).to receive(:color).with('POWERED_ON', :green)
|
40
|
+
subject.format_power_status(PowerStatus.new('POWERED_ON'))
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
context 'when the power is "POWERED_OFF"' do
|
45
|
+
it 'displays with red' do
|
46
|
+
expect(subject.ui).to receive(:color).with('POWERED_OFF', :red)
|
47
|
+
subject.format_power_status(PowerStatus.new('POWERED_OFF'))
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
context 'when the power is "SUSPENDED"' do
|
52
|
+
it 'displays with red' do
|
53
|
+
expect(subject.ui).to receive(:color).with('SUSPENDED', :yellow)
|
54
|
+
subject.format_power_status(PowerStatus.new('SUSPENDED'))
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
describe '#format_memory_value' do
|
60
|
+
context 'when the memory value is 8192' do
|
61
|
+
it 'displays as 8,192' do
|
62
|
+
expect(subject.ui).to receive(:text).with('8,192')
|
63
|
+
subject.format_memory_value(8192)
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
67
|
+
end
|
metadata
ADDED
@@ -0,0 +1,257 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: knife-vcenter
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 1.0.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Chef Partner Engineering
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2017-08-28 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: chef
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '12'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '12'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: knife-cloud
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '1.2'
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '1.2'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: rb-readline
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0.5'
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0.5'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: rbvmomi
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '1.11'
|
62
|
+
type: :runtime
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - "~>"
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '1.11'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: savon
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - "~>"
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '2.11'
|
76
|
+
type: :runtime
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - "~>"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '2.11'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: vsphere-automation-sdk
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - "~>"
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '2.5'
|
90
|
+
type: :runtime
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - "~>"
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '2.5'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: bundler
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - "~>"
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '1.7'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - "~>"
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '1.7'
|
111
|
+
- !ruby/object:Gem::Dependency
|
112
|
+
name: debase
|
113
|
+
requirement: !ruby/object:Gem::Requirement
|
114
|
+
requirements:
|
115
|
+
- - ">="
|
116
|
+
- !ruby/object:Gem::Version
|
117
|
+
version: '0'
|
118
|
+
type: :development
|
119
|
+
prerelease: false
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
requirements:
|
122
|
+
- - ">="
|
123
|
+
- !ruby/object:Gem::Version
|
124
|
+
version: '0'
|
125
|
+
- !ruby/object:Gem::Dependency
|
126
|
+
name: github_changelog_generator
|
127
|
+
requirement: !ruby/object:Gem::Requirement
|
128
|
+
requirements:
|
129
|
+
- - ">="
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: '0'
|
132
|
+
type: :development
|
133
|
+
prerelease: false
|
134
|
+
version_requirements: !ruby/object:Gem::Requirement
|
135
|
+
requirements:
|
136
|
+
- - ">="
|
137
|
+
- !ruby/object:Gem::Version
|
138
|
+
version: '0'
|
139
|
+
- !ruby/object:Gem::Dependency
|
140
|
+
name: pry
|
141
|
+
requirement: !ruby/object:Gem::Requirement
|
142
|
+
requirements:
|
143
|
+
- - ">="
|
144
|
+
- !ruby/object:Gem::Version
|
145
|
+
version: '0'
|
146
|
+
type: :development
|
147
|
+
prerelease: false
|
148
|
+
version_requirements: !ruby/object:Gem::Requirement
|
149
|
+
requirements:
|
150
|
+
- - ">="
|
151
|
+
- !ruby/object:Gem::Version
|
152
|
+
version: '0'
|
153
|
+
- !ruby/object:Gem::Dependency
|
154
|
+
name: rake
|
155
|
+
requirement: !ruby/object:Gem::Requirement
|
156
|
+
requirements:
|
157
|
+
- - "~>"
|
158
|
+
- !ruby/object:Gem::Version
|
159
|
+
version: '10.0'
|
160
|
+
type: :development
|
161
|
+
prerelease: false
|
162
|
+
version_requirements: !ruby/object:Gem::Requirement
|
163
|
+
requirements:
|
164
|
+
- - "~>"
|
165
|
+
- !ruby/object:Gem::Version
|
166
|
+
version: '10.0'
|
167
|
+
- !ruby/object:Gem::Dependency
|
168
|
+
name: rubocop
|
169
|
+
requirement: !ruby/object:Gem::Requirement
|
170
|
+
requirements:
|
171
|
+
- - "~>"
|
172
|
+
- !ruby/object:Gem::Version
|
173
|
+
version: '0.35'
|
174
|
+
type: :development
|
175
|
+
prerelease: false
|
176
|
+
version_requirements: !ruby/object:Gem::Requirement
|
177
|
+
requirements:
|
178
|
+
- - "~>"
|
179
|
+
- !ruby/object:Gem::Version
|
180
|
+
version: '0.35'
|
181
|
+
- !ruby/object:Gem::Dependency
|
182
|
+
name: ruby-debug-ide
|
183
|
+
requirement: !ruby/object:Gem::Requirement
|
184
|
+
requirements:
|
185
|
+
- - "~>"
|
186
|
+
- !ruby/object:Gem::Version
|
187
|
+
version: 0.6.0
|
188
|
+
type: :development
|
189
|
+
prerelease: false
|
190
|
+
version_requirements: !ruby/object:Gem::Requirement
|
191
|
+
requirements:
|
192
|
+
- - "~>"
|
193
|
+
- !ruby/object:Gem::Version
|
194
|
+
version: 0.6.0
|
195
|
+
description: Knife plugin to VMware vCenter.
|
196
|
+
email:
|
197
|
+
- partnereng@chef.io
|
198
|
+
executables: []
|
199
|
+
extensions: []
|
200
|
+
extra_rdoc_files: []
|
201
|
+
files:
|
202
|
+
- ".github/ISSUE_TEMPLATE.md"
|
203
|
+
- ".github/PULL_REQUEST_TEMPLATE.md"
|
204
|
+
- ".gitignore"
|
205
|
+
- ".rubocop.yml"
|
206
|
+
- ".travis.yml"
|
207
|
+
- CHANGELOG.md
|
208
|
+
- Gemfile
|
209
|
+
- LICENSE.txt
|
210
|
+
- README.md
|
211
|
+
- Rakefile
|
212
|
+
- knife-vcenter.gemspec
|
213
|
+
- lib/base.rb
|
214
|
+
- lib/chef/knife/cloud/vcenter_service.rb
|
215
|
+
- lib/chef/knife/cloud/vcenter_service_helpers.rb
|
216
|
+
- lib/chef/knife/cloud/vcenter_service_options.rb
|
217
|
+
- lib/chef/knife/vcenter_cluster_list.rb
|
218
|
+
- lib/chef/knife/vcenter_datacenter_list.rb
|
219
|
+
- lib/chef/knife/vcenter_host_list.rb
|
220
|
+
- lib/chef/knife/vcenter_vm_clone.rb
|
221
|
+
- lib/chef/knife/vcenter_vm_create.rb
|
222
|
+
- lib/chef/knife/vcenter_vm_delete.rb
|
223
|
+
- lib/chef/knife/vcenter_vm_list.rb
|
224
|
+
- lib/chef/knife/vcenter_vm_show.rb
|
225
|
+
- lib/knife-vcenter/version.rb
|
226
|
+
- lib/lookup_service_helper.rb
|
227
|
+
- lib/sso.rb
|
228
|
+
- lib/support/clone_vm.rb
|
229
|
+
- spec/spec_helper.rb
|
230
|
+
- spec/unit/vcenter_vm_list_spec.rb
|
231
|
+
homepage: https://github.com/chef/knife-vcenter
|
232
|
+
licenses:
|
233
|
+
- Apache 2.0
|
234
|
+
metadata: {}
|
235
|
+
post_install_message:
|
236
|
+
rdoc_options: []
|
237
|
+
require_paths:
|
238
|
+
- lib
|
239
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
240
|
+
requirements:
|
241
|
+
- - ">="
|
242
|
+
- !ruby/object:Gem::Version
|
243
|
+
version: '0'
|
244
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
245
|
+
requirements:
|
246
|
+
- - ">="
|
247
|
+
- !ruby/object:Gem::Version
|
248
|
+
version: '0'
|
249
|
+
requirements: []
|
250
|
+
rubyforge_project:
|
251
|
+
rubygems_version: 2.6.11
|
252
|
+
signing_key:
|
253
|
+
specification_version: 4
|
254
|
+
summary: Knife plugin to VMware vCenter.
|
255
|
+
test_files:
|
256
|
+
- spec/spec_helper.rb
|
257
|
+
- spec/unit/vcenter_vm_list_spec.rb
|