can anyone confirm whether Pants engine allows tap...
# development
f
can anyone confirm whether Pants engine allows tapping into / intercepting / recording the errors that the Pants process fails with?
1
The use case is as follows: a user runs a Pants command and it fails with an error, e.g.
DependencyRuleActionDeniedError
if there are visibility violations or
UnownedDependencyError
if Pants cannot infer owners for some imports. Not every user is going to be closely familiar with the error and their meaning. Most likely, Pants admins will have some internal documentation / troubleshooting guide tailored to the engineering organization jargon / context. So what I'd like to do is to print in the console an epilogue message depending on the error raised. I've experimented with the plugins model, but can't seem to find a way to post-process a failure raised by a rule.
this could look something like this:
Copy code
❯ pants dependencies ::
12:44:06.76 [ERROR] 1 Exception encountered:

Engine traceback:
  in `dependencies` goal

DependencyRuleActionDeniedError: cheeseshop/cli/utils/utils.py has 1 dependency violation:

  * cheeseshop/cli/utils/BUILD[!*] -> cheeseshop/repository/parsing : DENY
    python_sources cheeseshop/cli/utils/utils.py -> python_sources cheeseshop/repository/parsing/casts.py

--------------------------------------------------------------------------------------------------------------
To learn more about the visibility rules violations, please see <https://mycompany.org/development-guidelines/pants#visibility>.
b
You could likely monkeypatch the type in your plugin 🤷‍♂️
I think in the distant future, there's a lot of more pre- and post- thing plugin touch points.
f
You could likely monkeypatch the type in your plugin
I am sorry, could you please provide an example? I don't think I understand how this would be used in a rule
c
from rule code it is easy, just try this:
Copy code
async def some_rule() -> RetType:
    try:
        await Get(...)
    except (IntrinsicError, ...) as e:
        log.error("Bam")
    return ...
f
But this would not log an error when calling pants dependencies ::, would it?
c
ah no, I just skimmed the question and caught a “from rule” in there… as Josh more accurately replied we do not yet have good introspection/hookability in general for rule edges.
f
I see. Thanks! I'll file an issue on GitHub for us
b
In your
rules
body, monkeypatch the exception type to append your special message when initialized
f
oh do you mean something like this, @bitter-ability-32190
Copy code
class MyExc(DependencyRulesError):
    def __call__(self, *args, **kwargs):
        1/0

@rule
def epilogue_visibility_error() -> ???:
    from pants.engine.internals import dep_rules
    dep_rules.DependencyRuleActionDeniedError = MyExc
@curved-television-6568, do you know what return type my rule will have so that it's guaranteed to be executed when evaluating the dependencies?
b
That's the idea. You'll want to put it someplace: • That gets executed early • That is guaranteed to be called So I suggest putting it inside
def rules()
😉
coke 1
c
I think you’ll want to do the monkey patching when the plugin is registered..
there’s no way to have a plugin rule guranteed to be called for any and all rules, that I’m aware of at least…
1
f
oh great, thanks for the suggestion
So I suggest putting it inside
def rules()
I see it's being called, just need to confirm that I can keep the parts that are there and only extend with extra behavior
this worked lovely!
Copy code
from pants.engine import target
    class DependencyRuleActionDeniedError(Exception):
        @classmethod
        def create(cls, description_of_origin: str) -> 'DependencyRuleActionDeniedError':
            return cls(f"Dependency rule violation for {description_of_origin}")

        def __init__(self, message):
            super(DependencyRuleActionDeniedError, self).__init__(message + "\n\n" + epilogue_visibility_violation())

    target.DependencyRuleActionDeniedError = DependencyRuleActionDeniedError
    return collect_rules()
yields
Copy code
$ ./pants --no-pantsd dependencies ::

17:47:23.58 [ERROR] 1 Exception encountered:

Engine traceback:
  in `dependencies` goal

DependencyRuleActionDeniedError: cheeseshop/cli/utils/utils.py has 1 dependency violation:

  * cheeseshop/cli/utils/BUILD[!*] -> cheeseshop/repository/parsing : DENY
    python_sources cheeseshop/cli/utils/utils.py -> python_sources cheeseshop/repository/parsing/casts.py

------------------------------------------------------
To learn how to fix visibility rules violations, visit
<https://org.com/pants-url-help>
------------------------------------------------------
thanks very much Joshua and Andreas!
b
For the record, it's a hack. But also, meh
f
yep, I'm filing a GH issue for the future
not sure if this is something that will be done, but worth recording, I think
c
sweet. Flexing Pythons.. 😉