-
Notifications
You must be signed in to change notification settings - Fork 16.4k
feature(providers): added OpsgenieNotifier
#35530
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feature(providers): added OpsgenieNotifier
#35530
Conversation
|
Congratulations on your first Pull Request and welcome to the Apache Airflow community! If you have any issues or are unsure about any anything please check our Contribution Guide (https://github.com/apache/airflow/blob/main/CONTRIBUTING.rst)
|
| alias: str | None = None, | ||
| description: str | None = None, | ||
| responders: list[dict] | None = None, | ||
| visible_to: list[dict] | None = None, | ||
| actions: list[str] | None = None, | ||
| tags: list[str] | None = None, | ||
| details: dict | None = None, | ||
| entity: str | None = None, | ||
| source: str | None = None, | ||
| priority: str | None = None, | ||
| user: str | None = None, | ||
| note: str | None = None, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure maybe from user perspective better to have single payload: dict | None = None attribute rather than multiple attributes which later on combined into the single one payload?
Just a question, I'm never use Opsgenie Provider.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just a question, I'm never use Opsgenie Provider.
For now, me neither, but I'll be a user soon, so that's why I have decided to open this PR.
From a software engineering perspective I feel that this approach works best because it's easier to see what's optional and what isn't, and also the types of each parameter in case you forget. It also makes its usage nearly identical to the OpsgenieCreateAlertOperator, so there is no learning curve if someone wants to swap it for this notifier. And besides that there is always dict unpacking if someone already has a payload and wants to use it in this notifier.
I'm open to suggestions, though!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Building on what @Taragolis said, just one downside, you always have to keep up with the Opsgenie service. In the event that one of the parameters gets deprecated, someone has to make the change here and you would always have to keep up with the changes.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How do you propose I deal with the required params following the payload: dict | None = None approach, @utkarsharma2?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we wont have some hints (optional) we could create TypedDict, and use it as payload type something like payload: CreateAlertPayload
from typing import TypedDict
from typing_extensions import NotRequired # For compat with Python < 3.11
class CreateAlertPayload(TypedDict):
message: str
alias: NotRequired[str]
description: NotRequired[None]
responders: NotRequired[list[dict]]
visible_to: NotRequired[list[dict]]
actions: NotRequired[list[str]]
tags: NotRequired[list[str]]
details: NotRequired[dict]
entity: NotRequired[str]
source: NotRequired[str]
priority: NotRequired[str]
user: NotRequired[str]
note: NotRequired[str]There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@Taragolis also, how do we make sure that the template_fields will be able to be templated?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where do you think it could go? I was thinking a common.py file inside the provider so that it could be reused by the OpsgenieCreateAlertOperator, but I'm open to suggestions.
Maybe something opsgenie_typing.py and place CreateAlertPayload there, just suggestion just because: There are only two hard things in Computer Science: cache invalidation and naming things.
How do we deal with the opsgenie_conn_id?
Connection id usually (always?) is the separate parameter. so keep it as it is.
Make payload as single dictionary could be better by the reason which @utkarsharma2 mentioned.
how do we make sure that the template_fields will be able to be templated?
If you put payload attribute (or whatever it named) as part of template_fields then it would be templated. e.g.
send_opsgenie_notification(
payload={
"message": "Something went wrong in {{ dag.dag_id }}!"
"user": "{{var.value.user }}"
)There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Won't making payload a template_field also make the iterable fields templated? Would that be ok?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done adding the payload arg.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As you can see from the sad path, it's been hard to ensure the schema for payload with TypedDict. Is it the only way to go, @Taragolis?
|
Need to fix Static Checks, you could run locally You could have a look what failed in Tests / Static checks (pull_request) logs Also need to add into the Guides toctree this line Notifications <notifications/index>Under the Operators airflow/docs/apache-airflow-providers-opsgenie/index.rst Lines 32 to 37 in 22d5834
|
docs/apache-airflow-providers-opsgenie/notifications/opsgenie_notifier.rst
Outdated
Show resolved
Hide resolved
| alias: str | None = None, | ||
| description: str | None = None, | ||
| responders: list[dict] | None = None, | ||
| visible_to: list[dict] | None = None, | ||
| actions: list[str] | None = None, | ||
| tags: list[str] | None = None, | ||
| details: dict | None = None, | ||
| entity: str | None = None, | ||
| source: str | None = None, | ||
| priority: str | None = None, | ||
| user: str | None = None, | ||
| note: str | None = None, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Building on what @Taragolis said, just one downside, you always have to keep up with the Opsgenie service. In the event that one of the parameters gets deprecated, someone has to make the change here and you would always have to keep up with the changes.
Co-authored-by: Utkarsh Sharma <utkarsharma2@gmail.com>
Taragolis
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Need to fix static checks and documentation.
Better use pre-commit which save a lot of time, because when it run some of static checks might fixed during checks.
docs/apache-airflow-providers-opsgenie/notifications/opsgenie_notifier.rst
Outdated
Show resolved
Hide resolved
Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
…notifier.rst Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
docs/apache-airflow-providers-opsgenie/notifications/opsgenie_notifier.rst
Outdated
Show resolved
Hide resolved
| with pytest.raises(Exception): # should raise exception because message is a required key | ||
| notifier = OpsgenieNotifier(payload=config_no_message) | ||
| notifier({"dag": dag}) | ||
| mock_opsgenie_alert_hook.return_value.create_alert.assert_called_once_with( | ||
| expected_payload_dict_no_message | ||
| ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well it would not raise any error because you mock OpsgenieAlertHook.get_conn
What we actually want to test here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If payload really requires message at all times, as it should. Look at my inline comment there
should raise exception because message is a required key
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But this behaviour depend on upstream library which you mocks, so this error never happen in tests
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As result tests failed
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My point here that we should not tests upstream library exceptions, because it could changed in the future.
…notifier.rst Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
|
Awesome work, congrats on your first merged pull request! You are invited to check our Issue Tracker for additional contributions. |
--------- Co-authored-by: Utkarsh Sharma <utkarsharma2@gmail.com> Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>
--------- Co-authored-by: Utkarsh Sharma <utkarsharma2@gmail.com> Co-authored-by: Andrey Anshin <Andrey.Anshin@taragol.is>



closes: #35516
Added an
OpsgenieNotifier.It is almost the exact same implementation as
OpsgenieCreateAlertOperator, but given that now notifiers exist, I assumed it was better off as a notifier.Sample usage:
^ Add meaningful description above
Read the Pull Request Guidelines for more information.
In case of fundamental code changes, an Airflow Improvement Proposal (AIP) is needed.
In case of a new dependency, check compliance with the ASF 3rd Party License Policy.
In case of backwards incompatible changes please leave a note in a newsfragment file, named
{pr_number}.significant.rstor{issue_number}.significant.rst, in newsfragments.