{"record":{"id":"04467b2f5cc86572","repo":"puppetlabs/puppet","slug":"the-object-type-originator-label-inherits-fro","errorCode":null,"errorMessage":"The Object type '#{originator.label}' inherits from itself","messagePattern":"The Object type '#(.+?)' inherits from itself","errorType":"exception","errorClass":"Puppet::Error","httpStatus":null,"severity":"error","filePath":"lib/puppet/pops/types/p_object_type.rb","lineNumber":1005,"sourceCode":"    @equality_include_type\n  end\n\n  # Returns the functions of this `Object` type. If _include_parent_ is `true`, then all\n  # inherited functions will be included in the returned `Hash`.\n  #\n  # @param include_parent [Boolean] `true` if inherited functions should be included\n  # @return [Hash{String=>PFunction}] a hash with the functions\n  # @api public\n  def functions(include_parent = false)\n    get_members(include_parent, :functions)\n  end\n\n  DEFAULT = PObjectType.new(EMPTY_HASH)\n  # Assert that this type does not inherit from itself\n  # @api private\n  def check_self_recursion(originator)\n    unless @parent.nil?\n      raise Puppet::Error, \"The Object type '#{originator.label}' inherits from itself\" if @parent.equal?(originator)\n\n      @parent.check_self_recursion(originator)\n    end\n  end\n\n  # @api private\n  def label\n    @name || 'Object'\n  end\n\n  # @api private\n  def resolved_parent\n    parent = @parent\n    while parent.is_a?(PTypeAliasType)\n      parent = parent.resolved_type\n    end\n    parent\n  end","sourceCodeStart":987,"sourceCodeEnd":1023,"githubUrl":"https://github.com/puppetlabs/puppet/blob/e227c27540975c25aa22d533a52424a9d2fc886a/lib/puppet/pops/types/p_object_type.rb#L987-L1023","documentation":"Before resolving an Object type's parent chain, check_self_recursion walks upward through @parent links and raises Puppet::Error if the chain returns to the type that started the walk. Both direct self-parenting (parent => own name) and longer cycles (A's parent is B, B's parent is A) are caught.","triggerScenarios":"type MyApp::Node = Object[{ parent => 'MyApp::Node', ... }] (self-reference, often a copy-paste artifact), or two types in different files each naming the other as parent. The check runs during type resolution, before members are merged.","commonSituations":"Cloning a type definition and forgetting to update the parent; renaming types so old parent references now point at each other; generated type hierarchies emitted with cyclic parent links.","solutions":["Inspect the parent declarations of every type named in the error and break the loop: a type must ultimately derive from Object or another acyclic base","If you cloned a type, change the clone's parent to the actual base type","For generated code, emit a topological ordering check so cycles are caught at generation time"],"exampleFix":"# before\ntype MyApp::Node = Object[{\n  parent => 'MyApp::Node',   # inherits from itself\n  attributes => { name => String }\n}]\n\n# after\ntype MyApp::Node = Object[{\n  parent => 'MyApp::Base',\n  attributes => { name => String }\n}]","handlingStrategy":"validation","validationCode":"# walk the parent chain and detect cycles before resolution\ndef cyclic?(type, seen = {})\n  parent = type.instance_variable_get(:@parent)\n  return false if parent.nil?\n  return true if seen.key?(parent.label)\n  seen[type.label] = true\n  cyclic?(parent, seen)\nend\nraise 'parent cycle detected' if cyclic?(my_type)","typeGuard":null,"tryCatchPattern":"begin\n  Puppet::Pops::Types::PObjectType.new(name, init_hash)\nrescue Puppet::Error => e\n  raise unless e.message =~ /inherits from itself/\n  raise  # e.message names the loop head; break the parent cycle\nend","preventionTips":["After cloning or renaming types, grep all parent => references for self-links","For generated type hierarchies, topologically sort before emitting definitions"],"tags":["puppet","pcore","object-type","inheritance","cycle"],"backgroundTag":"circular-inheritance","analyzedSha":"e227c27540975c25aa22d533a52424a9d2fc886a","analyzedAt":"2026-08-21T20:49:46.650Z","schemaVersion":2},"datasetVersion":"2026-08-21T23:17:16.201Z"}