Skip to content

Commit

Permalink
Merge branch 'master' into bugfix/slack-update-incident-modal
Browse files Browse the repository at this point in the history
  • Loading branch information
whitdog47 authored Dec 20, 2024
2 parents c620561 + 6ee9b19 commit c86b6f0
Show file tree
Hide file tree
Showing 5 changed files with 69 additions and 37 deletions.
2 changes: 1 addition & 1 deletion src/dispatch/plugins/dispatch_slack/case/interactive.py
Original file line number Diff line number Diff line change
Expand Up @@ -1697,7 +1697,7 @@ def handle_user_mention(
users_not_in_case = []
for user_id in mentioned_users:
user_email = dispatch_slack_service.get_user_email(client, user_id)
if not participant_service.get_by_case_id_and_email(
if user_email and not participant_service.get_by_case_id_and_email(
db_session=db_session, case_id=context["subject"].id, email=user_email
):
users_not_in_case.append(user_email)
Expand Down
60 changes: 35 additions & 25 deletions src/dispatch/plugins/dispatch_slack/incident/interactive.py
Original file line number Diff line number Diff line change
Expand Up @@ -794,9 +794,12 @@ def handle_timeline_added_event(
# if user is not found, we default to "Unknown"
try:
message_sender_email = get_user_email(client=client, user_id=message_sender_id)
individual = individual_service.get_by_email_and_project(
db_session=db_session, email=message_sender_email, project_id=incident.project.id
)
if message_sender_email:
individual = individual_service.get_by_email_and_project(
db_session=db_session,
email=message_sender_email,
project_id=incident.project.id,
)
except Exception:
individual = None

Expand Down Expand Up @@ -1076,12 +1079,13 @@ def handle_member_joined_channel(
if inviter and inviter_is_user:
# Participant is added into the incident channel using an @ message or /invite command.
inviter_email = get_user_email(client=client, user_id=inviter)
added_by_participant = participant_service.get_by_incident_id_and_email(
db_session=db_session, incident_id=context["subject"].id, email=inviter_email
)
participant.added_by = added_by_participant
if inviter_email:
added_by_participant = participant_service.get_by_incident_id_and_email(
db_session=db_session, incident_id=context["subject"].id, email=inviter_email
)
participant.added_by = added_by_participant

else:
if not participant.added_by:
# User joins via the `join` button on Web Application or Slack.
# We default to the incident commander when we don't know who added the user or the user is the Dispatch bot.
incident = incident_service.get(
Expand Down Expand Up @@ -1129,14 +1133,15 @@ def handle_member_joined_channel(
if inviter and inviter_is_user:
# Participant is added into the incident channel using an @ message or /invite command.
inviter_email = get_user_email(client=client, user_id=inviter)
added_by_participant = participant_service.get_by_case_id_and_email(
db_session=db_session,
case_id=context["subject"].id,
email=inviter_email,
)
participant.added_by = added_by_participant
if inviter_email:
added_by_participant = participant_service.get_by_case_id_and_email(
db_session=db_session,
case_id=context["subject"].id,
email=inviter_email,
)
participant.added_by = added_by_participant

else:
if not participant.added_by:
# User joins via the `join` button on Web Application or Slack.
# We default to the incident commander when we don't know who added the user or the user is the Dispatch bot.
participant.added_by = case.assignee
Expand Down Expand Up @@ -1565,7 +1570,9 @@ def handle_assign_role_submission_event(
ack_assign_role_submission_event(ack=ack)
assignee_user_id = form_data[AssignRoleBlockIds.user]["value"]
assignee_role = form_data[AssignRoleBlockIds.role]["value"]
assignee_email = get_user_email(client=client, user_id=assignee_user_id)
assignee_email = (
get_user_email(client=client, user_id=assignee_user_id) or "[email protected]"
)

# we assign the role
incident_flows.incident_assign_role_flow(
Expand Down Expand Up @@ -2556,15 +2563,18 @@ def handle_incident_notification_subscribe_button_click(
user_id = context["user_id"]
user_email = get_user_email(client=client, user_id=user_id)

if incident.tactical_group:
group_flows.update_group(
subject=incident,
group=incident.tactical_group,
group_action=GroupAction.add_member,
group_member=user_email,
db_session=db_session,
)
message = f"Success! We've subscribed you to incident {incident.name}. You will start receiving all tactical reports about this incident via email."
if not user_email:
message = "Sorry, we can't invite you to this incident. There was a problem finding your user."
else:
if incident.tactical_group:
group_flows.update_group(
subject=incident,
group=incident.tactical_group,
group_action=GroupAction.add_member,
group_member=user_email,
db_session=db_session,
)
message = f"Success! We've subscribed you to incident {incident.name}. You will start receiving all tactical reports about this incident via email."

respond(text=message, response_type="ephemeral", replace_original=False, delete_original=False)

Expand Down
4 changes: 2 additions & 2 deletions src/dispatch/plugins/dispatch_slack/service.py
Original file line number Diff line number Diff line change
Expand Up @@ -274,10 +274,10 @@ def get_user_profile_by_email(client: WebClient, email: str) -> SlackResponse:
return _get_user_profile_by_email(WebClientWrapper(client), email)


def get_user_email(client: WebClient, user_id: str) -> str:
def get_user_email(client: WebClient, user_id: str) -> str | None:
"""Gets the user's email."""
user_info = get_user_info_by_id(client, user_id)
return user_info["profile"]["email"]
return user_info["profile"].get("email")


def get_user_avatar_url(client: WebClient, email: str) -> str:
Expand Down
4 changes: 2 additions & 2 deletions src/dispatch/workflow/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
Pagination,
)
from dispatch.participant.models import ParticipantRead
from dispatch.plugin.models import PluginInstance, PluginInstanceRead
from dispatch.plugin.models import PluginInstance, PluginInstanceReadMinimal
from dispatch.project.models import ProjectRead

from .enums import WorkflowInstanceStatus
Expand Down Expand Up @@ -121,7 +121,7 @@ class WorkflowSignal(DispatchBase):
class WorkflowBase(DispatchBase):
name: NameStr
resource_id: str
plugin_instance: PluginInstanceRead
plugin_instance: PluginInstanceReadMinimal
parameters: Optional[List[dict]] = []
enabled: Optional[bool]
description: Optional[str] = Field(None, nullable=True)
Expand Down
36 changes: 29 additions & 7 deletions src/dispatch/workflow/views.py
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
from fastapi import APIRouter, HTTPException, status
from fastapi import APIRouter, HTTPException, status, Depends
from pydantic.error_wrappers import ErrorWrapper, ValidationError

from dispatch.database.core import DbSession
from dispatch.database.service import CommonParameters, search_filter_sort_paginate
from dispatch.auth.permissions import SensitiveProjectActionPermission, PermissionsDependency
from dispatch.exceptions import NotFoundError
from dispatch.models import PrimaryKey
from dispatch.plugin import service as plugin_service
Expand All @@ -27,7 +28,10 @@ def get_workflows(common: CommonParameters):
return search_filter_sort_paginate(model="Workflow", **common)


@router.get("/{workflow_id}", response_model=WorkflowRead)
@router.get(
"/{workflow_id}",
response_model=WorkflowRead,
)
def get_workflow(db_session: DbSession, workflow_id: PrimaryKey):
"""Get a workflow."""
workflow = get(db_session=db_session, workflow_id=workflow_id)
Expand All @@ -39,7 +43,10 @@ def get_workflow(db_session: DbSession, workflow_id: PrimaryKey):
return workflow


@router.get("/instances/{workflow_instance_id}", response_model=WorkflowInstanceRead)
@router.get(
"/instances/{workflow_instance_id}",
response_model=WorkflowInstanceRead,
)
def get_workflow_instance(db_session: DbSession, workflow_instance_id: PrimaryKey):
"""Get a workflow instance."""
workflow_instance = get_instance(db_session=db_session, instance_id=workflow_instance_id)
Expand All @@ -51,7 +58,11 @@ def get_workflow_instance(db_session: DbSession, workflow_instance_id: PrimaryKe
return workflow_instance


@router.post("", response_model=WorkflowRead)
@router.post(
"",
response_model=WorkflowRead,
dependencies=[Depends(PermissionsDependency([SensitiveProjectActionPermission]))],
)
def create_workflow(db_session: DbSession, workflow_in: WorkflowCreate):
"""Create a new workflow."""
plugin_instance = plugin_service.get_instance(
Expand All @@ -66,7 +77,11 @@ def create_workflow(db_session: DbSession, workflow_in: WorkflowCreate):
return create(db_session=db_session, workflow_in=workflow_in)


@router.put("/{workflow_id}", response_model=WorkflowRead)
@router.put(
"/{workflow_id}",
response_model=WorkflowRead,
dependencies=[Depends(PermissionsDependency([SensitiveProjectActionPermission]))],
)
def update_workflow(db_session: DbSession, workflow_id: PrimaryKey, workflow_in: WorkflowUpdate):
"""Update a workflow."""
workflow = get(db_session=db_session, workflow_id=workflow_id)
Expand All @@ -78,7 +93,11 @@ def update_workflow(db_session: DbSession, workflow_id: PrimaryKey, workflow_in:
return update(db_session=db_session, workflow=workflow, workflow_in=workflow_in)


@router.delete("/{workflow_id}", response_model=None)
@router.delete(
"/{workflow_id}",
response_model=None,
dependencies=[Depends(PermissionsDependency([SensitiveProjectActionPermission]))],
)
def delete_workflow(db_session: DbSession, workflow_id: PrimaryKey):
"""Delete a workflow."""
workflow = get(db_session=db_session, workflow_id=workflow_id)
Expand All @@ -90,7 +109,10 @@ def delete_workflow(db_session: DbSession, workflow_id: PrimaryKey):
delete(db_session=db_session, workflow_id=workflow_id)


@router.post("/{workflow_id}/run", response_model=WorkflowInstanceRead)
@router.post(
"/{workflow_id}/run",
response_model=WorkflowInstanceRead,
)
def run_workflow(
db_session: DbSession,
workflow_id: PrimaryKey,
Expand Down

0 comments on commit c86b6f0

Please sign in to comment.