Class: Puppet::Pops::Types::PTypeAliasType
- Inherits:
-
PAnyType
- Object
- TypedModelObject
- PAnyType
- Puppet::Pops::Types::PTypeAliasType
- Defined in:
- lib/puppet/pops/types/types.rb
Overview
Describes a named alias for another Type. The alias is created with a name and an unresolved type expression. The type expression may in turn contain other aliases (including the alias that contains it) which means that an alias might contain self recursion. Whether or not that is the case is computed and remembered when the alias is resolved since guarding against self recursive constructs is relatively expensive.
Defined Under Namespace
Classes: AssertOtherTypeAcceptor, AssertSelfRecursionStatusAcceptor
Instance Attribute Summary collapse
- #loader ⇒ Object readonly
- #name ⇒ Object readonly
Class Method Summary collapse
Instance Method Summary collapse
- #accept(visitor, guard) ⇒ Object
- #assignable?(o, guard = nil) ⇒ Boolean
- #callable_args?(callable, guard) ⇒ Boolean
- #check_self_recursion(originator) ⇒ Object
- #eql?(o) ⇒ Boolean
- #hash ⇒ Object
-
#initialize(name, type_expr, resolved_type = nil) ⇒ PTypeAliasType
constructor
A new instance of PTypeAliasType.
- #instance?(o, guard = nil) ⇒ Boolean
- #iterable?(guard = nil) ⇒ Boolean
- #iterable_type(guard = nil) ⇒ Object
- #kind_of_callable?(optional = true, guard = nil) ⇒ Boolean
-
#method_missing(name, *arguments, &block) ⇒ Object
Delegates to resolved type.
- #really_instance?(o, guard = nil) ⇒ Boolean private
-
#resolve(loader) ⇒ PTypeAliasType
private
Called from the TypeParser once it has found a type using the Loader.
-
#resolved_type ⇒ PAnyType
Returns the resolved type.
-
#respond_to_missing?(name, include_private) ⇒ Boolean
Delegates to resolved type.
- #self_recursion? ⇒ Boolean
- #set_self_recursion_status ⇒ Object
-
#to_s ⇒ String
Returns the expanded string the form of the alias, e.g.
-
#type_expr ⇒ Object
private
‘nil` to prevent serialization of the type_expr used when first initializing this instance.
Methods inherited from PAnyType
#==, #callable?, #callable_with?, create, #create, #generalize, new_function, #normalize, #roundtrip_with_string?, #simple_name, simple_name, #to_alias_expanded_s
Methods inherited from TypedModelObject
_pcore_type, create_ptype, register_ptypes
Methods included from PuppetObject
#_pcore_all_contents, #_pcore_contents, #_pcore_init_hash, #_pcore_type
Constructor Details
#initialize(name, type_expr, resolved_type = nil) ⇒ PTypeAliasType
Returns a new instance of PTypeAliasType.
3371 3372 3373 3374 3375 3376 |
# File 'lib/puppet/pops/types/types.rb', line 3371 def initialize(name, type_expr, resolved_type = nil) @name = name @type_expr = type_expr @resolved_type = resolved_type @self_recursion = false end |
Dynamic Method Handling
This class handles dynamic methods through the method_missing method
#method_missing(name, *arguments, &block) ⇒ Object
Delegates to resolved type
3540 3541 3542 3543 |
# File 'lib/puppet/pops/types/types.rb', line 3540 def method_missing(name, *arguments, &block) super if @resolved_type.equal?(PTypeReferenceType::DEFAULT) resolved_type.send(name, *arguments, &block) end |
Instance Attribute Details
#loader ⇒ Object (readonly)
3366 3367 3368 |
# File 'lib/puppet/pops/types/types.rb', line 3366 def loader @loader end |
#name ⇒ Object (readonly)
3366 3367 3368 |
# File 'lib/puppet/pops/types/types.rb', line 3366 def name @name end |
Class Method Details
.register_ptype(loader, ir) ⇒ Object
3355 3356 3357 3358 3359 3360 3361 3362 3363 3364 |
# File 'lib/puppet/pops/types/types.rb', line 3355 def self.register_ptype(loader, ir) create_ptype(loader, ir, 'AnyType', 'name' => PStringType::NON_EMPTY, 'type_expr' => PAnyType::DEFAULT, 'resolved_type' => { KEY_TYPE => POptionalType.new(PTypeType::DEFAULT), KEY_VALUE => nil } ) end |
Instance Method Details
#accept(visitor, guard) ⇒ Object
3515 3516 3517 3518 3519 3520 |
# File 'lib/puppet/pops/types/types.rb', line 3515 def accept(visitor, guard) guarded_recursion(guard, nil) do |g| super(visitor, g) @resolved_type.accept(visitor, g) unless @resolved_type.nil? end end |
#assignable?(o, guard = nil) ⇒ Boolean
3378 3379 3380 3381 3382 3383 3384 3385 |
# File 'lib/puppet/pops/types/types.rb', line 3378 def assignable?(o, guard = nil) if @self_recursion guard ||= RecursionGuard.new guard.with_this(self) { |state| state == RecursionGuard::SELF_RECURSION_IN_BOTH ? true : super(o, guard) } else super(o, guard) end end |
#callable_args?(callable, guard) ⇒ Boolean
3397 3398 3399 |
# File 'lib/puppet/pops/types/types.rb', line 3397 def callable_args?(callable, guard) guarded_recursion(guard, false) { |g| resolved_type.callable_args?(callable, g) } end |
#check_self_recursion(originator) ⇒ Object
3401 3402 3403 |
# File 'lib/puppet/pops/types/types.rb', line 3401 def check_self_recursion(originator) resolved_type.check_self_recursion(originator) unless originator.equal?(self) end |
#eql?(o) ⇒ Boolean
3511 3512 3513 |
# File 'lib/puppet/pops/types/types.rb', line 3511 def eql?(o) super && o.name == @name end |
#hash ⇒ Object
3421 3422 3423 |
# File 'lib/puppet/pops/types/types.rb', line 3421 def hash @name.hash end |
#instance?(o, guard = nil) ⇒ Boolean
3409 3410 3411 |
# File 'lib/puppet/pops/types/types.rb', line 3409 def instance?(o, guard = nil) really_instance?(o, guard) == 1 end |
#iterable?(guard = nil) ⇒ Boolean
3413 3414 3415 |
# File 'lib/puppet/pops/types/types.rb', line 3413 def iterable?(guard = nil) guarded_recursion(guard, false) { |g| resolved_type.iterable?(g) } end |
#iterable_type(guard = nil) ⇒ Object
3417 3418 3419 |
# File 'lib/puppet/pops/types/types.rb', line 3417 def iterable_type(guard = nil) guarded_recursion(guard, nil) { |g| resolved_type.iterable_type(g) } end |
#kind_of_callable?(optional = true, guard = nil) ⇒ Boolean
3405 3406 3407 |
# File 'lib/puppet/pops/types/types.rb', line 3405 def kind_of_callable?(optional=true, guard = nil) guarded_recursion(guard, false) { |g| resolved_type.kind_of_callable?(optional, g) } end |
#really_instance?(o, guard = nil) ⇒ Boolean
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
3546 3547 3548 3549 3550 3551 3552 3553 3554 3555 |
# File 'lib/puppet/pops/types/types.rb', line 3546 def really_instance?(o, guard = nil) if @self_recursion guard ||= RecursionGuard.new guard.with_that(o) do guard.with_this(self) { |state| state == RecursionGuard::SELF_RECURSION_IN_BOTH ? 0 : resolved_type.really_instance?(o, guard) } end else resolved_type.really_instance?(o, guard) end end |
#resolve(loader) ⇒ PTypeAliasType
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Called from the TypeParser once it has found a type using the Loader. The TypeParser will interpret the contained expression and the resolved type is remembered. This method also checks and remembers if the resolve type contains self recursion.
3471 3472 3473 3474 3475 3476 3477 3478 3479 3480 3481 3482 3483 3484 3485 3486 3487 3488 3489 3490 3491 3492 3493 3494 3495 3496 3497 3498 3499 3500 3501 3502 3503 3504 3505 3506 3507 3508 3509 |
# File 'lib/puppet/pops/types/types.rb', line 3471 def resolve(loader) @loader = loader if @resolved_type.nil? # resolved to PTypeReferenceType::DEFAULT during resolve to avoid endless recursion @resolved_type = PTypeReferenceType::DEFAULT @self_recursion = true # assumed while it being found out below begin if @type_expr.is_a?(PTypeReferenceType) @resolved_type = @type_expr.resolve(loader) else @resolved_type = TypeParser.singleton.interpret(@type_expr, loader).normalize end # Find out if this type is recursive. A recursive type has performance implications # on several methods and this knowledge is used to avoid that for non-recursive # types. guard = RecursionGuard.new real_type_asserter = AssertOtherTypeAcceptor.new accept(real_type_asserter, guard) unless real_type_asserter.other_type_detected? raise ArgumentError, "Type alias '#{name}' cannot be resolved to a real type" end @self_recursion = guard.recursive_this?(self) # All aliases involved must re-check status since this alias is now resolved if @self_recursion accept(AssertSelfRecursionStatusAcceptor.new, RecursionGuard.new) when_self_recursion_detected end rescue @resolved_type = nil raise end else # An alias may appoint an Object type that isn't resolved yet. The default type # reference is used to prevent endless recursion and should not be resolved here. @resolved_type.resolve(loader) unless @resolved_type.equal?(PTypeReferenceType::DEFAULT) end self end |
#resolved_type ⇒ PAnyType
Returns the resolved type. The type must have been resolved by a call prior to calls to this method or an error will be raised.
3392 3393 3394 3395 |
# File 'lib/puppet/pops/types/types.rb', line 3392 def resolved_type raise Puppet::Error, "Reference to unresolved type #{@name}" unless @resolved_type @resolved_type end |
#respond_to_missing?(name, include_private) ⇒ Boolean
Delegates to resolved type
3535 3536 3537 |
# File 'lib/puppet/pops/types/types.rb', line 3535 def respond_to_missing?(name, include_private) resolved_type.respond_to?(name, include_private) end |
#self_recursion? ⇒ Boolean
3522 3523 3524 |
# File 'lib/puppet/pops/types/types.rb', line 3522 def self_recursion? @self_recursion end |
#set_self_recursion_status ⇒ Object
3454 3455 3456 3457 3458 3459 3460 3461 |
# File 'lib/puppet/pops/types/types.rb', line 3454 def set_self_recursion_status return if @self_recursion || @resolved_type.is_a?(PTypeReferenceType) @self_recursion = true guard = RecursionGuard.new accept(NoopTypeAcceptor::INSTANCE, guard) @self_recursion = guard.recursive_this?(self) when_self_recursion_detected if @self_recursion # no difference end |
#to_s ⇒ String
Returns the expanded string the form of the alias, e.g. <alias name> = <resolved type>
3530 3531 3532 |
# File 'lib/puppet/pops/types/types.rb', line 3530 def to_s TypeFormatter.singleton.(self) end |
#type_expr ⇒ Object
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Returns ‘nil` to prevent serialization of the type_expr used when first initializing this instance.
3559 3560 3561 |
# File 'lib/puppet/pops/types/types.rb', line 3559 def type_expr nil end |