Skip to content

Unrecognized attribute in target gives error that doesn't squelch stacktrace #518

@ericzundel

Description

@ericzundel

I ran 'pants' the other day and got an exception that was difficult to read.

Exception message: __init__() got an unexpected keyword argument 'resources'

There are a few of problems I noticed:

  • The stack trace was not suppressed as I expected it to be (I didn't have --print-exception-stacktrace enable)
  • The name of the BUILD file with the error is buried in the middle of the exception
  • The overall impression of the error makes this look like a bug in pants itself, not invalid BUILD file semantics.

The actual output looked something like this.

~/Src/Pants master * devpants goal compile src/python/pants
*** Running pants in dev mode from /Users/zundel/Src/pants/src/python/pants/bin/pants_exe.py ***
Traceback (most recent call last):
  File "/Users/zundel/Src/pants/src/python/pants/base/build_graph.py", line 341, in target_addressable_to_target
    **addressable.kwargs)
  File "/Users/zundel/Src/pants/src/python/pants/backend/core/targets/dependencies.py", line 33, in __init__
    super(Dependencies, self).__init__(payload=EmptyPayload(), *args, **kwargs)
TypeError: __init__() got an unexpected keyword argument 'resources'
ERROR:pants.base.build_graph:Failed to instantiate Target with type <class 'pants.backend.core.targets.dependencies.Dependencies'> with name "pants" at address BuildFileAddress(/Users/zundel/Src/pants/src/python/pants/BUILD, pants)
Traceback (most recent call last):
  File "/Users/zundel/Src/pants/src/python/pants/base/build_graph.py", line 341, in target_addressable_to_target
    **addressable.kwargs)
  File "/Users/zundel/Src/pants/src/python/pants/backend/core/targets/dependencies.py", line 33, in __init__
    super(Dependencies, self).__init__(payload=EmptyPayload(), *args, **kwargs)
TypeError: __init__() got an unexpected keyword argument 'resources'

Exception message: __init__() got an unexpected keyword argument 'resources'

Here is a change that reproduces the problem:

 git diff
diff --git a/src/python/pants/BUILD b/src/python/pants/BUILD
index 325ae1f..e9eaef6 100644
--- a/src/python/pants/BUILD
+++ b/src/python/pants/BUILD
@@ -3,6 +3,7 @@

 target(
   name = 'pants',
+  resources = [],
   dependencies = [
     'src/python/pants/bin:pants',
   ],

I saw some code in jar_publish that surrounds Target.get_all_targets() with a catch of (TypeError, ImportError, SyntaxError) in jar_publish.py but I think this code is out of date (there is not Target.get_all_targets() method!) , and catching that exception might already obscure a real bug in pants, I wouldn't want to replicate it.

Maybe we could just update the exception handler in build_graph.py to handle TypeError() with extra care?

Another thought I had is that we could add **kwargs to Target.__init__() and then explicitly look for extra keywords and formulate a more helpful error message. To keep from obscuring a bug in Pants source code, maybe we could inspect the Target instance and to see if this target has attributes that will tell us it came from a BUILD file, then raise a different exception. That's not very pretty (but neither is the error message we get today.) Unfortunately, I didn't see anything obvious to tell us at that level.

(Pdb) p self.__class__
<class 'pants.backend.core.targets.dependencies.Dependencies'>
(Pdb) p dir(self)
['LANG_DISCRIMINATORS', '__class__', '__delattr__', '__dict__', '__doc__', '__eq__', '__format__', '__getattribute__', '__hash__', '__init__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_propagate_exclusives', '_propagate_exclusives_work', 'add_labels', 'add_to_exclusives', 'assert_list', 'closure', 'combine_ids', 'compute_invalidation_hash', 'concrete_derived_from', 'dependencies', 'dependents', 'derived_from', 'get_addressable_type', 'get_all_exclusives', 'has_label', 'has_resources', 'has_sources', 'id', 'identifier', 'identify', 'inject_dependency', 'invalidation_hash', 'is_android', 'is_apt', 'is_codegen', 'is_exported', 'is_jar', 'is_jar_library', 'is_java', 'is_java_agent', 'is_jvm', 'is_jvm_app', 'is_original', 'is_python', 'is_scala', 'is_scalac_plugin', 'is_synthetic', 'is_test', 'is_thrift', 'lang_discriminator', 'mark_extra_invalidation_hash_dirty', 'mark_extra_transitive_invalidation_hash_dirty', 'mark_invalidation_hash_dirty', 'mark_transitive_invalidation_hash_dirty', 'maybe_readable_combine_ids', 'maybe_readable_identify', 'remove_label', 'sources_relative_to_buildroot', 'sources_relative_to_source_root', 'target_base', 'transitive_invalidation_hash', 'traversable_dependency_specs', 'traversable_specs', 'walk', 'with_description']

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions