Class: PortfolioInstance
- Inherits:
-
ArchDefObject
- Object
- ArchDefObject
- PortfolioInstance
- Defined in:
- lib/arch_obj_models/portfolio.rb
Overview
Holds information about a PortfolioInstance YAML file (certificate or profile). The inherited “data” member is the database of extensions, instructions, CSRs, etc.
Defined Under Namespace
Classes: ExtraNote, InScopeExtensionParameter, Recommendation, RevisionHistory
Instance Attribute Summary collapse
-
#arch_def ⇒ ArchDef
readonly
The defining ArchDef.
Instance Method Summary collapse
-
#all_in_scope_ext_params ⇒ Array<InScopeExtensionParameter>
These are always IN-SCOPE by definition (since they are listed in the portfolio).
-
#all_in_scope_exts_with_param(param) ⇒ Array<Extension>
All the in-scope extensions (those in the portfolio) that define this parameter in the database and the parameter is in-scope (listed in that extension’s list of parameters in the portfolio).
-
#all_in_scope_exts_without_param(param) ⇒ Array<Extension>
All the in-scope extensions (those in the portfolio) that define this parameter in the database but the parameter is out-of-scope (not listed in that extension’s list of parameters in the portfolio).
-
#all_out_of_scope_params ⇒ Array<ExtensionParameter>
Parameters out of scope across all in scope extensions (those listed in the portfolio).
- #description ⇒ Object
- #extension_note(ext_name) ⇒ String?
-
#extension_presence(ext_name) ⇒ String
Given an extension
ext_name
, return the presence as a string. - #extra_notes ⇒ Object
- #extra_notes_for_presence(desired_presence_obj) ⇒ String?
-
#in_scope_ext_params(ext_req) ⇒ Array<InScopeExtensionParameter>
These are always IN SCOPE by definition (since they are listed in the portfolio).
-
#in_scope_ext_reqs(desired_presence = nil) ⇒ Array<ExtensionRequirements>
If desired_presence is provided, only returns extensions with that presence.
-
#in_scope_extensions ⇒ Array<Extension>
List of all extensions listed in portfolio.
-
#initialize(data, arch_def) ⇒ PortfolioInstance
constructor
A new instance of PortfolioInstance.
- #mandatory_ext_reqs ⇒ Object
- #optional_ext_reqs ⇒ Object
- #optional_type_ext_reqs ⇒ Object
-
#out_of_scope_params(ext_name) ⇒ Array<ExtensionParameter>
Parameters that are out of scope for named extension.
- #recommendations ⇒ Object
- #revision_history ⇒ Object
-
#to_arch_def ⇒ ArchDef
A partially-configured architecture definition corresponding to this certificate.
-
#uses_optional_types? ⇒ Boolean
Does the profile differentiate between different types of optional.
-
#version ⇒ Gem::Version
Semantic version of the PortfolioInstance.
-
#version_strongest_presence(ext_name, ext_versions) ⇒ Array<String>
Returns the strongest presence string for each of the specified versions.
Constructor Details
#initialize(data, arch_def) ⇒ PortfolioInstance
Returns a new instance of PortfolioInstance.
54 55 56 57 |
# File 'lib/arch_obj_models/portfolio.rb', line 54 def initialize(data, arch_def) super(data) @arch_def = arch_def end |
Instance Attribute Details
#arch_def ⇒ ArchDef (readonly)
Returns The defining ArchDef.
50 51 52 |
# File 'lib/arch_obj_models/portfolio.rb', line 50 def arch_def @arch_def end |
Instance Method Details
#all_in_scope_ext_params ⇒ Array<InScopeExtensionParameter>
These are always IN-SCOPE by definition (since they are listed in the portfolio). Can have multiple array entries with the same parameter name since multiple extensions may define the same parameter.
270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 |
# File 'lib/arch_obj_models/portfolio.rb', line 270 def all_in_scope_ext_params return @all_in_scope_ext_params unless @all_in_scope_ext_params.nil? @all_in_scope_ext_params = [] @data["extensions"].each do |ext_name, ext_data| # Find Extension object from database ext = @arch_def.extension(ext_name) raise "Cannot find extension named #{ext_name}" if ext.nil? ext_data["parameters"]&.each do |param_name, param_data| param = ext.params.find { |p| p.name == param_name } raise "There is no param '#{param_name}' in extension '#{ext_name}" if param.nil? next unless ext.versions.any? do |ext_ver| Gem::Requirement.new(ext_data["version"]).satisfied_by?(ext_ver.version) && param.defined_in_extension_version?(ext_ver.version) end @all_in_scope_ext_params << InScopeExtensionParameter.new(param, param_data["schema"], param_data["note"]) end end @all_in_scope_ext_params end |
#all_in_scope_exts_with_param(param) ⇒ Array<Extension>
All the in-scope extensions (those in the portfolio) that define this parameter in the database and the parameter is in-scope (listed in that extension’s list of parameters in the portfolio).
359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 |
# File 'lib/arch_obj_models/portfolio.rb', line 359 def all_in_scope_exts_with_param(param) raise ArgumentError, "Expecting ExtensionParameter" unless param.is_a?(ExtensionParameter) exts = [] # Interate through all the extensions in the architecture database that define this parameter. param.exts.each do |ext| found = false in_scope_extensions.each do |in_scope_ext| if ext.name == in_scope_ext.name found = true next end end if found # Only add extensions that exist in this portfolio. exts << ext end end # Return intersection of extension names exts end |
#all_in_scope_exts_without_param(param) ⇒ Array<Extension>
All the in-scope extensions (those in the portfolio) that define this parameter in the database but the parameter is out-of-scope (not listed in that extension’s list of parameters in the portfolio).
388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 |
# File 'lib/arch_obj_models/portfolio.rb', line 388 def all_in_scope_exts_without_param(param) raise ArgumentError, "Expecting ExtensionParameter" unless param.is_a?(ExtensionParameter) exts = [] # Local variable, no caching # Interate through all the extensions in the architecture database that define this parameter. param.exts.each do |ext| found = false in_scope_extensions.each do |in_scope_ext| if ext.name == in_scope_ext.name found = true next end end if found # Only add extensions that are in-scope (i.e., exist in this portfolio). exts << ext end end # Return intersection of extension names exts end |
#all_out_of_scope_params ⇒ Array<ExtensionParameter>
Returns Parameters out of scope across all in scope extensions (those listed in the portfolio).
331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 |
# File 'lib/arch_obj_models/portfolio.rb', line 331 def all_out_of_scope_params return @all_out_of_scope_params unless @all_out_of_scope_params.nil? @all_out_of_scope_params = [] in_scope_ext_reqs.each do |ext_req| ext = @arch_def.extension(ext_req.name) ext.params.each do |param| next if all_in_scope_ext_params.any? { |c| c.param.name == param.name } next unless ext.versions.any? do |ext_ver| Gem::Requirement.new(ext_req.version_requirement).satisfied_by?(ext_ver.version) && param.defined_in_extension_version?(ext_ver.version) end @all_out_of_scope_params << param end end @all_out_of_scope_params end |
#description ⇒ Object
59 |
# File 'lib/arch_obj_models/portfolio.rb', line 59 def description = @data["description"] |
#extension_note(ext_name) ⇒ String?
100 101 102 103 104 105 106 |
# File 'lib/arch_obj_models/portfolio.rb', line 100 def extension_note(ext_name) # Get extension information from YAML for passed in extension name. ext_data = @data["extensions"][ext_name] raise "Cannot find extension named #{ext_name}" if ext_data.nil? return ext_data["note"] unless ext_data.nil? end |
#extension_presence(ext_name) ⇒ String
Returns Given an extension ext_name
, return the presence as a string. If the extension name isn’t found in the portfolio, return “-”.
66 67 68 69 70 71 |
# File 'lib/arch_obj_models/portfolio.rb', line 66 def extension_presence(ext_name) # Get extension information from YAML for passed in extension name. ext_data = @data["extensions"][ext_name] ext_data.nil? ? "-" : ExtensionPresence.new(ext_data["presence"]).to_s end |
#extra_notes ⇒ Object
456 457 458 459 460 461 462 463 464 |
# File 'lib/arch_obj_models/portfolio.rb', line 456 def extra_notes return @extra_notes unless @extra_notes.nil? @extra_notes = [] @data["extra_notes"]&.each do |extra_note| @extra_notes << ExtraNote.new(extra_note) end @extra_notes end |
#extra_notes_for_presence(desired_presence_obj) ⇒ String?
469 470 471 472 473 |
# File 'lib/arch_obj_models/portfolio.rb', line 469 def extra_notes_for_presence(desired_presence_obj) raise ArgumentError, "Expecting ExtensionPresence but got a #{desired_presence_obj.class}" unless desired_presence_obj.is_a?(ExtensionPresence) extra_notes.select {|extra_note| extra_note.presence_obj == desired_presence_obj} end |
#in_scope_ext_params(ext_req) ⇒ Array<InScopeExtensionParameter>
These are always IN SCOPE by definition (since they are listed in the portfolio).
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 |
# File 'lib/arch_obj_models/portfolio.rb', line 298 def in_scope_ext_params(ext_req) raise ArgumentError, "Expecting ExtensionRequirement" unless ext_req.is_a?(ExtensionRequirement) ext_params = [] # Local variable, no caching # Get extension information from portfolio YAML for passed in extension requirement. ext_data = @data["extensions"][ext_req.name] raise "Cannot find extension named #{ext_req.name}" if ext_data.nil? # Find Extension object from database ext = @arch_def.extension(ext_req.name) raise "Cannot find extension named #{ext_req.name}" if ext.nil? # Loop through an extension's parameter constraints (hash) from the portfolio. # Note that "&" is the Ruby safe navigation operator (i.e., skip do loop if nil). ext_data["parameters"]&.each do |param_name, param_data| # Find ExtensionParameter object from database ext_param = ext.params.find { |p| p.name == param_name } raise "There is no param '#{param_name}' in extension '#{ext_req.name}" if ext_param.nil? next unless ext.versions.any? do |ext_ver| Gem::Requirement.new(ext_data["version"]).satisfied_by?(ext_ver.version) && ext_param.defined_in_extension_version?(ext_ver.version) end ext_params << InScopeExtensionParameter.new(ext_param, param_data["schema"], param_data["note"]) end ext_params end |
#in_scope_ext_reqs(desired_presence = nil) ⇒ Array<ExtensionRequirements>
If desired_presence is provided, only returns extensions with that presence. If desired_presence is a String, only the presence portion of an ExtensionPresence is compared.
112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 |
# File 'lib/arch_obj_models/portfolio.rb', line 112 def in_scope_ext_reqs(desired_presence = nil) in_scope_ext_reqs = [] # Convert desired_present argument to ExtensionPresence object if not nil. desired_presence_converted = desired_presence.nil? ? nil : desired_presence.is_a?(String) ? desired_presence : desired_presence.is_a?(ExtensionPresence) ? desired_presence : ExtensionPresence.new(desired_presence) @data["extensions"]&.each do |ext_name, ext_data| actual_presence = ext_data["presence"] # Could be a String or Hash raise "Missing extension presence for extension #{ext_name}" if actual_presence.nil? # Convert String or Hash to object. actual_presence_obj = ExtensionPresence.new(actual_presence) match = if desired_presence.nil? true # Always match else actual_presence_obj == desired_presence_converted end if match in_scope_ext_reqs << ExtensionRequirement.new(ext_name, ext_data["version"], presence: actual_presence_obj, note: ext_data["note"], req_id: "REQ-EXT-" + ext_name) end end in_scope_ext_reqs end |
#in_scope_extensions ⇒ Array<Extension>
Returns List of all extensions listed in portfolio.
150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 |
# File 'lib/arch_obj_models/portfolio.rb', line 150 def in_scope_extensions return @in_scope_extensions unless @in_scope_extensions.nil? @in_scope_extensions = in_scope_ext_reqs.map do |er| obj = arch_def.extension(er.name) # @todo: change this to raise once all the profile extensions # are defined warn "Extension #{er.name} is not defined" if obj.nil? obj end.reject(&:nil?) @in_scope_extensions end |
#mandatory_ext_reqs ⇒ Object
145 |
# File 'lib/arch_obj_models/portfolio.rb', line 145 def mandatory_ext_reqs = in_scope_ext_reqs(ExtensionPresence.mandatory) |
#optional_ext_reqs ⇒ Object
146 |
# File 'lib/arch_obj_models/portfolio.rb', line 146 def optional_ext_reqs = in_scope_ext_reqs(ExtensionPresence.optional) |
#optional_type_ext_reqs ⇒ Object
147 |
# File 'lib/arch_obj_models/portfolio.rb', line 147 def optional_type_ext_reqs = in_scope_ext_reqs(ExtensionPresence.optional) |
#out_of_scope_params(ext_name) ⇒ Array<ExtensionParameter>
Returns Parameters that are out of scope for named extension.
352 353 354 |
# File 'lib/arch_obj_models/portfolio.rb', line 352 def out_of_scope_params(ext_name) all_out_of_scope_params.select{|param| param.exts.any? {|ext| ext.name == ext_name} } end |
#recommendations ⇒ Object
487 488 489 490 491 492 493 494 495 |
# File 'lib/arch_obj_models/portfolio.rb', line 487 def recommendations return @recommendations unless @recommendations.nil? @recommendations = [] @data["recommendations"]&.each do |recommendation| @recommendations << Recommendation.new(recommendation) end @recommendations end |
#revision_history ⇒ Object
431 432 433 434 435 436 437 438 439 |
# File 'lib/arch_obj_models/portfolio.rb', line 431 def revision_history return @revision_history unless @revision_history.nil? @revision_history = [] @data["revision_history"].each do |rev| @revision_history << RevisionHistory.new(rev) end @revision_history end |
#to_arch_def ⇒ ArchDef
Returns A partially-configured architecture definition corresponding to this certificate.
184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 |
# File 'lib/arch_obj_models/portfolio.rb', line 184 def to_arch_def return @generated_arch_def unless @generated_arch_def.nil? arch_def_data = arch_def.unconfigured_data arch_def_data["mandatory_extensions"] = mandatory_ext_reqs.map do |ext_req| { "name" => ext_req.name, "version" => ext_req.version_requirement.requirements.map { |r| "#{r[0]} #{r[1]}" } } end arch_def_data["params"] = all_in_scope_ext_params.select(&:single_value?).map { |p| [p.name, p.value] }.to_h # XXX Add list of prohibited_extensions file = Tempfile.new("archdef") file.write(YAML.safe_dump(arch_def_data, permitted_classes: [Date])) file.flush file.close @generated_arch_def = ArchDef.new(name, Pathname.new(file.path)) end |
#uses_optional_types? ⇒ Boolean
Returns Does the profile differentiate between different types of optional.
167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 |
# File 'lib/arch_obj_models/portfolio.rb', line 167 def uses_optional_types? return @uses_optional_types unless @uses_optional_types.nil? @uses_optional_types = false # Iterate through different kinds of optional using the "object" version (not the string version). ExtensionPresence.optional_types_obj.each do |optional_type_obj| # See if any extension reqs have this type of optional. unless in_scope_ext_reqs(optional_type_obj).empty? @uses_optional_types = true end end @uses_optional_types end |
#version ⇒ Gem::Version
Returns Semantic version of the PortfolioInstance.
62 |
# File 'lib/arch_obj_models/portfolio.rb', line 62 def version = Gem::Version.new(@data["version"]) |
#version_strongest_presence(ext_name, ext_versions) ⇒ Array<String>
Returns the strongest presence string for each of the specified versions.
77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 |
# File 'lib/arch_obj_models/portfolio.rb', line 77 def version_strongest_presence(ext_name, ext_versions) presences = [] # See if any extension requirement in this profile lists this version as either mandatory or optional. ext_versions.map do |v| mandatory = mandatory_ext_reqs.any? { |ext_req| ext_req.satisfied_by?(ext_name, v.version) } optional = optional_ext_reqs.any? { |ext_req| ext_req.satisfied_by?(ext_name, v.version) } # Just show strongest presence (mandatory stronger than optional). if mandatory presences << ExtensionPresence.mandatory elsif optional presences << ExtensionPresence.optional else presences << "-" end end presences end |