rbvmomi2 3.0.1 → 3.3.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d34ef12391cd295ad859e953162f145e58266a7ff08273af472c5c9a1d165fc9
4
- data.tar.gz: 661da76f808d7aa9ea90903c1c6f10157b19570a2ef74e9b9bc0ddfb30b1108f
3
+ metadata.gz: 3cd7c8f7c07cfc8e042bc125747b279ff88430ab531068b3bb56aeb937ec5009
4
+ data.tar.gz: 1c76cde83a228ac728cdd747b3367a32d19a2a98c7c07eb796a2a73fd414fd2b
5
5
  SHA512:
6
- metadata.gz: 8073e399abfc3dcabc569a9e80daad2ec2024dda355167c61fbded973b44f94b2b4474f8bf8ebe854b87e2e2e1514391202f0584d4f64664b8b123c4b2c462d3
7
- data.tar.gz: 5794ea5f1524626c144760feb120007eb95b9263efa95ebb8fd2f2dfa76638e4df9803c586e316fbb52a28ae107712775e9a76142a3e37e12e22306132ccae83
6
+ metadata.gz: d9779867969725d9d0eeb72fda7193e5a6e8725cc53a5d4c41518089203657ca7eb30ed8bbcf1f5e17f7a48aec52accbb975fb32e6d19a9a63c1c01d2796d560
7
+ data.tar.gz: 88421663c3b937da0fe46cb021c3f17830670738cb5297851db5ee3a0a605b994c5c12d3402b835d6418481f5348d4a6e3cb8a354d6cc67192597527bc8bcfad
data/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # RbVmomi
2
2
 
3
- [<img src="https://badge.fury.io/rb/rbvmomi.svg" alt="gem-version">](https://rubygems.org/gems/rbvmomi)
3
+ [<img src="https://badge.fury.io/rb/rbvmomi2.svg" alt="gem-version">](https://rubygems.org/gems/rbvmomi2)
4
4
  ![Test](https://github.com/ManageIQ/rbvmomi2/workflows/Test/badge.svg)
5
5
  ![Lint](https://github.com/ManageIQ/rbvmomi2/workflows/Lint/badge.svg)
6
6
  [<img src="https://badges.gitter.im/vmware/rbvmomi.svg">](https://gitter.im/vmware/rbvmomi)
@@ -195,8 +195,7 @@ module RbVmomi
195
195
  end
196
196
  xml
197
197
  rescue
198
- $stderr.puts "#{$!.class} while serializing #{name} (#{type}):"
199
- PP.pp o, $stderr
198
+ RbVmomi.logger.error("#{$!.class} while serializing #{name} (#{type})\n#{o.pretty_inspect}")
200
199
  raise
201
200
  end
202
201
 
@@ -221,8 +221,7 @@ module RbVmomi
221
221
  else raise "unexpected type #{t.inspect} (#{t.ancestors * '/'})"
222
222
  end
223
223
  rescue
224
- $stderr.puts "#{$!.class} while deserializing #{xml.name} (#{typename}):"
225
- $stderr.puts xml.to_s
224
+ RbVmomi.logger.error("#{$!.class} while deserializing #{xml.name} (#{typename}):\n#{xml.to_s}")
226
225
  raise
227
226
  end
228
227
 
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RbVmomi
4
+ class << self
5
+ attr_writer :logger
6
+ end
7
+
8
+ def self.logger
9
+ @logger ||= begin
10
+ require 'logger'
11
+ Logger.new($stderr)
12
+ end
13
+ end
14
+ end
data/lib/rbvmomi/pbm.rb CHANGED
@@ -18,7 +18,7 @@ module RbVmomi
18
18
  # @option opts [Boolean] :ssl (true) Whether to use SSL.
19
19
  # @option opts [Boolean] :insecure (false) If true, ignore SSL certificate errors.
20
20
  # @option opts [String] :path (/pbm/sdk) SDK endpoint path.
21
- # @option opts [Boolean] :debug (false) If true, print SOAP traffic to stderr.
21
+ # @option opts [Boolean] :debug (false) If true, print SOAP traffic to RbVmomi.logger.debug.
22
22
  def self.connect vim, opts = {}
23
23
  raise unless opts.is_a? Hash
24
24
 
data/lib/rbvmomi/sms.rb CHANGED
@@ -17,7 +17,7 @@ module RbVmomi
17
17
  # @option opts [Boolean] :ssl (true) Whether to use SSL.
18
18
  # @option opts [Boolean] :insecure (false) If true, ignore SSL certificate errors.
19
19
  # @option opts [String] :path (/sms/sdk) SDK endpoint path.
20
- # @option opts [Boolean] :debug (false) If true, print SOAP traffic to stderr.
20
+ # @option opts [Boolean] :debug (false) If true, print SOAP traffic to RbVmomi.logger.debug.
21
21
  def self.connect vim, opts = {}
22
22
  raise unless opts.is_a? Hash
23
23
 
@@ -84,11 +84,7 @@ class RbVmomi::TrivialSoap
84
84
  headers = { 'content-type' => 'text/xml; charset=utf-8', 'SOAPAction' => action }
85
85
  headers['cookie'] = @cookie if @cookie
86
86
 
87
- if @debug
88
- $stderr.puts 'Request:'
89
- $stderr.puts body
90
- $stderr.puts
91
- end
87
+ RbVmomi.logger.debug("Request:\n#{body}") if @debug
92
88
 
93
89
  if @cookie.nil? && @sso
94
90
  @sso.request_token unless @sso.assertion_id
@@ -112,11 +108,7 @@ class RbVmomi::TrivialSoap
112
108
 
113
109
  nk = Nokogiri(response.body)
114
110
 
115
- if @debug
116
- $stderr.puts "Response (in #{'%.3f' % (end_time - start_time)} s)"
117
- $stderr.puts nk
118
- $stderr.puts
119
- end
111
+ RbVmomi.logger.debug("Response (in #{'%.3f' % (end_time - start_time)} s)\n#{nk}") if @debug
120
112
 
121
113
  [nk.xpath('//soapenv:Body/*').select(&:element?).first, response.body.size]
122
114
  end
@@ -3,5 +3,5 @@
3
3
  # SPDX-License-Identifier: MIT
4
4
 
5
5
  module RbVmomi
6
- VERSION = '3.0.1'.freeze
6
+ VERSION = '3.3.0'.freeze
7
7
  end
data/lib/rbvmomi/vim.rb CHANGED
@@ -18,7 +18,7 @@ module RbVmomi
18
18
  # @option opts [String] :user (root) Username.
19
19
  # @option opts [String] :password Password.
20
20
  # @option opts [String] :path (/sdk) SDK endpoint path.
21
- # @option opts [Boolean] :debug (false) If true, print SOAP traffic to stderr.
21
+ # @option opts [Boolean] :debug (false) If true, print SOAP traffic to RbVmomi.logger.debug.
22
22
  # @option opts [String] :operation_id If set, use for operationID
23
23
  # @option opts [Boolean] :close_on_exit (true) If true, will close connection with at_exit
24
24
  # @option opts [RbVmomi::SSO] :sso (nil) Use SSO token to login if set
@@ -56,7 +56,7 @@ module RbVmomi
56
56
  def close
57
57
  serviceContent.sessionManager.Logout
58
58
  rescue RbVmomi::Fault => e
59
- $stderr.puts(e.message) if debug
59
+ RbVmomi.logger.error(e.message) if debug
60
60
  ensure
61
61
  self.cookie = nil
62
62
  super
data/lib/rbvmomi.rb CHANGED
@@ -12,6 +12,7 @@ module RbVmomi
12
12
  end
13
13
 
14
14
  require_relative 'rbvmomi/connection'
15
+ require_relative 'rbvmomi/logging'
15
16
  require_relative 'rbvmomi/sso'
16
17
  require_relative 'rbvmomi/version'
17
18
  require_relative 'rbvmomi/vim'
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative './vmodl_helper'
4
+
5
+ namespace :vmodl do
6
+ desc 'Verify vmodl.db'
7
+ task :verify do
8
+ VmodlHelper.verify!
9
+ end
10
+
11
+ desc 'Generate vmodl.db'
12
+ task :generate do
13
+ VmodlHelper.generate!
14
+ end
15
+ end
@@ -0,0 +1,206 @@
1
+ # frozen_string_literal: true
2
+ require 'active_support/core_ext/enumerable'
3
+ require 'active_support/inflector'
4
+ require 'optimist'
5
+ require 'pathname'
6
+ require 'wsdl/parser'
7
+ require 'rbvmomi'
8
+ require 'rbvmomi/pbm'
9
+ require 'rbvmomi/sms'
10
+
11
+ class VmodlHelper
12
+ class << self
13
+ def verify!
14
+ run!('verify')
15
+ end
16
+
17
+ def generate!
18
+ run!('generate')
19
+ end
20
+
21
+ private
22
+
23
+ def run!(mode)
24
+ vmodl, wsdl = options(mode).values_at(:vmodl, :wsdl)
25
+ new(vmodl_path: vmodl, wsdl_path: wsdl).send("#{mode}!")
26
+ end
27
+
28
+ def options(rake_task)
29
+ argv = ARGV.slice_after('--').to_a.last
30
+ Optimist.options(argv) do
31
+ educate_on_error
32
+ opt :wsdl, 'Path to the vsphere-ws wsdl file', type: :string, required: true
33
+ opt :vmodl, 'Path to the vmodl.db', type: :string, default: 'vmodl.db'
34
+ banner <<~EOS
35
+ Usage:
36
+ rake vmodl:#{rake_task} -- --wsdl=path/to/wsdl
37
+ EOS
38
+ end
39
+ end
40
+ end
41
+
42
+ def initialize(vmodl_path:, wsdl_path:)
43
+ @vmodl_path = Pathname.new(vmodl_path)
44
+ @wsdl_path = Pathname.new(wsdl_path)
45
+
46
+ @vmodl = load_vmodl(@vmodl_path)
47
+ @wsdl = load_wsdl(@wsdl_path)
48
+ end
49
+
50
+ def verify!
51
+ # Loop through the ComplexTypes in the WSDL and compare their types
52
+ # to the types which are defined in the vmodl.db
53
+ wsdl_types_by_name.each_value do |type|
54
+ type_name = type.name.name
55
+ vmodl_data = @vmodl[type_name]
56
+
57
+ # If a type exists in the WSDL but not in the vmodl.db this usually
58
+ # indicates that it was added in a newer version than the current
59
+ # vmodl.db supports.
60
+ #
61
+ # Print a warning that the type is missing and skip it.
62
+ if vmodl_data.nil?
63
+ puts " #{type_name} is missing"
64
+ next
65
+ end
66
+
67
+ # Index the properties by name to make it simpler to find later
68
+ elements_by_name = type.elements.index_by { |e| e.name.name }
69
+
70
+ # Loop through the properties defined in the vmodl.db for this type and
71
+ # compare the type to that property as defined in the wsdl.
72
+ vmodl_data['props'].each do |vmodl_prop|
73
+ wsdl_prop = elements_by_name[vmodl_prop['name']]
74
+ next if wsdl_prop.nil?
75
+
76
+ vmodl_klass = wsdl_constantize(vmodl_prop['wsdl_type'])
77
+ wsdl_klass = wsdl_constantize(wsdl_prop.type.source)
78
+
79
+ # The vmodl class should be equal to or a subclass of the one in the wsdl.
80
+ # Example of a subclass is e.g. VirtualMachine.host is defined as a HostSystem
81
+ # in the vmodl.db but it is a ManagedObjectReference in the wsdl.
82
+ puts "#{type_name}.#{vmodl_prop["name"]} #{wsdl_klass.wsdl_name} doesn't match #{vmodl_klass.wsdl_name}" unless vmodl_klass <= wsdl_klass
83
+ end
84
+ end
85
+ end
86
+
87
+ def generate!
88
+ wsdl_types_by_name.each_value do |type|
89
+ type_name = type.name.name
90
+ vmodl_data = @vmodl[type_name]
91
+
92
+ if vmodl_data.nil?
93
+ base_class = wsdl_types_by_name[type.complexcontent.extension.base.name]
94
+ inherited_properties = base_class.elements.map { |element| element.name.name }
95
+ properties = type.elements.reject { |e| inherited_properties.include?(e.name.name) }
96
+
97
+ vmodl_data = {
98
+ 'kind' => 'data',
99
+ 'props' => properties.map do |element|
100
+ {
101
+ 'name' => element.name.name,
102
+ 'is-optional' => element.minoccurs == 0,
103
+ 'is-array' => element.maxoccurs != 1,
104
+ 'version-id-ref' => nil,
105
+ 'wsdl_type' => wsdl_to_vmodl_type(element.type)
106
+ }
107
+ end,
108
+ 'wsdl_base' => type.complexcontent.extension.base.name
109
+ }
110
+
111
+ @vmodl[type_name] = vmodl_data
112
+ @vmodl['_typenames']['_typenames'] << type_name
113
+
114
+ puts "Adding #{type_name} to vmodl"
115
+
116
+ wsdl_to_rbvmomi_namespace(type).loader.add_types type_name => vmodl_data
117
+ end
118
+ end
119
+
120
+ wsdl_types_by_name.each_value do |type|
121
+ type_name = type.name.name
122
+ vmodl_data = @vmodl[type_name]
123
+
124
+ elements_by_name = type.elements.index_by { |e| e.name.name }
125
+
126
+ # Loop through the properties defined in the vmodl.db for this type and
127
+ # compare the type to that property as defined in the wsdl.
128
+ vmodl_data['props'].each do |vmodl_prop|
129
+ wsdl_prop = elements_by_name[vmodl_prop['name']]
130
+ next if wsdl_prop.nil?
131
+
132
+ vmodl_klass = wsdl_constantize(vmodl_prop['wsdl_type'])
133
+ wsdl_klass = wsdl_constantize(wsdl_prop.type.source)
134
+
135
+ vmodl_prop['wsdl_type'] = wsdl_klass.wsdl_name unless vmodl_klass <= wsdl_klass
136
+ end
137
+ end
138
+
139
+ dump_vmodl!
140
+ end
141
+
142
+ protected
143
+
144
+ def load_wsdl(path)
145
+ # WSDL includes have to resolve in the local directory so we have to
146
+ # change working directories to where the wsdl is
147
+ Dir.chdir(path.dirname) do
148
+ WSDL::Parser.new.parse(path.read)
149
+ end
150
+ end
151
+
152
+ def load_vmodl(path)
153
+ Marshal.load(path.read)
154
+ end
155
+
156
+ def dump_vmodl!
157
+ File.write(@vmodl_path, Marshal.dump(@vmodl))
158
+ end
159
+
160
+ private
161
+
162
+ def wsdl_types_by_name
163
+ @wsdl_types_by_name ||= @wsdl.collect_complextypes
164
+ .reject { |type| type.name.name.match?(/^ArrayOf|RequestType$/) }
165
+ .index_by { |type| type.name.name }
166
+ end
167
+
168
+ def wsdl_to_vmodl_type(type)
169
+ case type.source
170
+ when /vim25:/, /pbm:/, /sms:/
171
+ vmodl_type = type.name == 'ManagedObjectReference' ? 'ManagedObject' : type.name
172
+ when /xsd:/
173
+ vmodl_type = type.source
174
+ else
175
+ raise ArgumentError, "Unrecognized wsdl type: [#{type}]"
176
+ end
177
+
178
+ vmodl_type
179
+ end
180
+
181
+ def wsdl_to_rbvmomi_namespace(type)
182
+ case type.targetnamespace
183
+ when 'urb:vim25'
184
+ RbVmomi::VIM
185
+ when 'urn:pbm'
186
+ RbVmomi::PBM
187
+ when 'urn:sms'
188
+ RbVmomi::SMS
189
+ else
190
+ raise ArgumentError, "Unrecognized namespace [#{type}]"
191
+ end
192
+ end
193
+
194
+ # Normalize the type, some of these don't have RbVmomi equivalents such as xsd:long
195
+ # and RbVmomi uses ManagedObjects not ManagedObjectReferences as parameters
196
+ def wsdl_constantize(type)
197
+ type = type.split(':').last
198
+ type = 'int' if %w[long short byte].include?(type)
199
+ type = 'float' if type == 'double'
200
+ type = 'binary' if type == 'base64Binary'
201
+ type = 'ManagedObject' if type == 'ManagedObjectReference'
202
+
203
+ type = type.camelcase
204
+ type.safe_constantize || "RbVmomi::BasicTypes::#{type}".safe_constantize || "RbVmomi::VIM::#{type}".safe_constantize
205
+ end
206
+ end
data/vmodl.db CHANGED
Binary file
metadata CHANGED
@@ -1,15 +1,15 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rbvmomi2
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.1
4
+ version: 3.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Adam Grare
8
8
  - Jason Frey
9
- autorequire:
9
+ autorequire:
10
10
  bindir: exe
11
11
  cert_chain: []
12
- date: 2021-09-23 00:00:00.000000000 Z
12
+ date: 2022-03-10 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: builder
@@ -43,16 +43,22 @@ dependencies:
43
43
  name: nokogiri
44
44
  requirement: !ruby/object:Gem::Requirement
45
45
  requirements:
46
+ - - ">="
47
+ - !ruby/object:Gem::Version
48
+ version: 1.12.5
46
49
  - - "~>"
47
50
  - !ruby/object:Gem::Version
48
- version: '1.10'
51
+ version: '1.12'
49
52
  type: :runtime
50
53
  prerelease: false
51
54
  version_requirements: !ruby/object:Gem::Requirement
52
55
  requirements:
56
+ - - ">="
57
+ - !ruby/object:Gem::Version
58
+ version: 1.12.5
53
59
  - - "~>"
54
60
  - !ruby/object:Gem::Version
55
- version: '1.10'
61
+ version: '1.12'
56
62
  - !ruby/object:Gem::Dependency
57
63
  name: optimist
58
64
  requirement: !ruby/object:Gem::Requirement
@@ -179,7 +185,7 @@ dependencies:
179
185
  - - "~>"
180
186
  - !ruby/object:Gem::Version
181
187
  version: 0.9.25
182
- description:
188
+ description:
183
189
  email:
184
190
  - adam@grare.com
185
191
  - fryguy9@gmail.com
@@ -196,6 +202,7 @@ files:
196
202
  - lib/rbvmomi/connection.rb
197
203
  - lib/rbvmomi/deserialization.rb
198
204
  - lib/rbvmomi/fault.rb
205
+ - lib/rbvmomi/logging.rb
199
206
  - lib/rbvmomi/optimist.rb
200
207
  - lib/rbvmomi/pbm.rb
201
208
  - lib/rbvmomi/sms.rb
@@ -231,12 +238,14 @@ files:
231
238
  - lib/rbvmomi/vim/Task.rb
232
239
  - lib/rbvmomi/vim/VirtualMachine.rb
233
240
  - lib/rbvmomi2.rb
241
+ - lib/tasks/vmodl.rake
242
+ - lib/tasks/vmodl_helper.rb
234
243
  - vmodl.db
235
244
  homepage: https://github.com/ManageIQ/rbvmomi2
236
245
  licenses:
237
246
  - MIT
238
247
  metadata: {}
239
- post_install_message:
248
+ post_install_message:
240
249
  rdoc_options: []
241
250
  require_paths:
242
251
  - lib
@@ -251,8 +260,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
251
260
  - !ruby/object:Gem::Version
252
261
  version: '0'
253
262
  requirements: []
254
- rubygems_version: 3.2.5
255
- signing_key:
263
+ rubygems_version: 3.3.5
264
+ signing_key:
256
265
  specification_version: 4
257
266
  summary: Ruby interface to the VMware vSphere API
258
267
  test_files: []