microsoft-agents-activity 0.7.0.dev0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- microsoft_agents/activity/__init__.py +200 -0
- microsoft_agents/activity/_channel_id_field_mixin.py +95 -0
- microsoft_agents/activity/_load_configuration.py +33 -0
- microsoft_agents/activity/_model_utils.py +64 -0
- microsoft_agents/activity/_type_aliases.py +7 -0
- microsoft_agents/activity/_utils/__init__.py +6 -0
- microsoft_agents/activity/_utils/_deferred_string.py +34 -0
- microsoft_agents/activity/action_types.py +17 -0
- microsoft_agents/activity/activity.py +787 -0
- microsoft_agents/activity/activity_event_names.py +9 -0
- microsoft_agents/activity/activity_importance.py +10 -0
- microsoft_agents/activity/activity_types.py +25 -0
- microsoft_agents/activity/adaptive_card_invoke_action.py +27 -0
- microsoft_agents/activity/adaptive_card_invoke_response.py +23 -0
- microsoft_agents/activity/adaptive_card_invoke_value.py +25 -0
- microsoft_agents/activity/agents_model.py +49 -0
- microsoft_agents/activity/animation_card.py +57 -0
- microsoft_agents/activity/attachment.py +27 -0
- microsoft_agents/activity/attachment_data.py +24 -0
- microsoft_agents/activity/attachment_info.py +22 -0
- microsoft_agents/activity/attachment_layout_types.py +9 -0
- microsoft_agents/activity/attachment_view.py +18 -0
- microsoft_agents/activity/audio_card.py +57 -0
- microsoft_agents/activity/basic_card.py +33 -0
- microsoft_agents/activity/caller_id_constants.py +10 -0
- microsoft_agents/activity/card_action.py +42 -0
- microsoft_agents/activity/card_image.py +22 -0
- microsoft_agents/activity/channel_account.py +39 -0
- microsoft_agents/activity/channel_adapter_protocol.py +79 -0
- microsoft_agents/activity/channel_id.py +95 -0
- microsoft_agents/activity/channels.py +161 -0
- microsoft_agents/activity/contact_relation_update_action_types.py +9 -0
- microsoft_agents/activity/conversation_account.py +41 -0
- microsoft_agents/activity/conversation_members.py +19 -0
- microsoft_agents/activity/conversation_parameters.py +40 -0
- microsoft_agents/activity/conversation_reference.py +69 -0
- microsoft_agents/activity/conversation_resource_response.py +22 -0
- microsoft_agents/activity/conversation_update_types.py +18 -0
- microsoft_agents/activity/conversations_result.py +20 -0
- microsoft_agents/activity/delivery_modes.py +12 -0
- microsoft_agents/activity/end_of_conversation_codes.py +13 -0
- microsoft_agents/activity/entity/__init__.py +36 -0
- microsoft_agents/activity/entity/ai_entity.py +111 -0
- microsoft_agents/activity/entity/entity.py +41 -0
- microsoft_agents/activity/entity/entity_types.py +14 -0
- microsoft_agents/activity/entity/geo_coordinates.py +33 -0
- microsoft_agents/activity/entity/mention.py +24 -0
- microsoft_agents/activity/entity/place.py +33 -0
- microsoft_agents/activity/entity/product_info.py +20 -0
- microsoft_agents/activity/entity/thing.py +21 -0
- microsoft_agents/activity/error.py +22 -0
- microsoft_agents/activity/error_response.py +15 -0
- microsoft_agents/activity/errors/__init__.py +14 -0
- microsoft_agents/activity/errors/error_message.py +64 -0
- microsoft_agents/activity/errors/error_resources.py +52 -0
- microsoft_agents/activity/expected_replies.py +16 -0
- microsoft_agents/activity/fact.py +21 -0
- microsoft_agents/activity/hero_card.py +33 -0
- microsoft_agents/activity/inner_http_error.py +17 -0
- microsoft_agents/activity/input_hints.py +10 -0
- microsoft_agents/activity/installation_update_action_types.py +9 -0
- microsoft_agents/activity/invoke_response.py +27 -0
- microsoft_agents/activity/media_card.py +57 -0
- microsoft_agents/activity/media_event_value.py +15 -0
- microsoft_agents/activity/media_url.py +19 -0
- microsoft_agents/activity/message_reaction.py +16 -0
- microsoft_agents/activity/message_reaction_types.py +14 -0
- microsoft_agents/activity/message_update_types.py +10 -0
- microsoft_agents/activity/oauth_card.py +27 -0
- microsoft_agents/activity/paged_members_result.py +19 -0
- microsoft_agents/activity/receipt_card.py +39 -0
- microsoft_agents/activity/receipt_item.py +38 -0
- microsoft_agents/activity/resource_response.py +15 -0
- microsoft_agents/activity/role_types.py +12 -0
- microsoft_agents/activity/semantic_action.py +21 -0
- microsoft_agents/activity/semantic_actions_states.py +10 -0
- microsoft_agents/activity/sign_in_constants.py +13 -0
- microsoft_agents/activity/sign_in_resource.py +17 -0
- microsoft_agents/activity/signin_card.py +19 -0
- microsoft_agents/activity/suggested_actions.py +21 -0
- microsoft_agents/activity/teams/__init__.py +198 -0
- microsoft_agents/activity/teams/app_based_link_query.py +18 -0
- microsoft_agents/activity/teams/batch_failed_entries_response.py +15 -0
- microsoft_agents/activity/teams/batch_failed_entry.py +16 -0
- microsoft_agents/activity/teams/batch_operation_response.py +13 -0
- microsoft_agents/activity/teams/batch_operation_state_response.py +24 -0
- microsoft_agents/activity/teams/bot_config_auth.py +18 -0
- microsoft_agents/activity/teams/cache_info.py +18 -0
- microsoft_agents/activity/teams/cancel_operation_response.py +19 -0
- microsoft_agents/activity/teams/channel_info.py +21 -0
- microsoft_agents/activity/teams/config_auth_response.py +17 -0
- microsoft_agents/activity/teams/config_response.py +18 -0
- microsoft_agents/activity/teams/config_response_base.py +14 -0
- microsoft_agents/activity/teams/config_task_response.py +18 -0
- microsoft_agents/activity/teams/conversation_list.py +17 -0
- microsoft_agents/activity/teams/file_consent_card.py +24 -0
- microsoft_agents/activity/teams/file_consent_card_response.py +21 -0
- microsoft_agents/activity/teams/file_download_info.py +24 -0
- microsoft_agents/activity/teams/file_info_card.py +21 -0
- microsoft_agents/activity/teams/file_upload_info.py +26 -0
- microsoft_agents/activity/teams/meeting_details.py +23 -0
- microsoft_agents/activity/teams/meeting_details_base.py +21 -0
- microsoft_agents/activity/teams/meeting_end_event_details.py +15 -0
- microsoft_agents/activity/teams/meeting_event_details.py +15 -0
- microsoft_agents/activity/teams/meeting_info.py +24 -0
- microsoft_agents/activity/teams/meeting_notification.py +15 -0
- microsoft_agents/activity/teams/meeting_notification_base.py +14 -0
- microsoft_agents/activity/teams/meeting_notification_channel_data.py +16 -0
- microsoft_agents/activity/teams/meeting_notification_recipient_failure_info.py +20 -0
- microsoft_agents/activity/teams/meeting_notification_response.py +20 -0
- microsoft_agents/activity/teams/meeting_participant_info.py +18 -0
- microsoft_agents/activity/teams/meeting_participants_event_details.py +16 -0
- microsoft_agents/activity/teams/meeting_stage_surface.py +25 -0
- microsoft_agents/activity/teams/meeting_start_event_details.py +15 -0
- microsoft_agents/activity/teams/meeting_tab_icon_surface.py +15 -0
- microsoft_agents/activity/teams/message_actions_payload.py +70 -0
- microsoft_agents/activity/teams/message_actions_payload_app.py +29 -0
- microsoft_agents/activity/teams/message_actions_payload_attachment.py +30 -0
- microsoft_agents/activity/teams/message_actions_payload_body.py +17 -0
- microsoft_agents/activity/teams/message_actions_payload_conversation.py +20 -0
- microsoft_agents/activity/teams/message_actions_payload_from.py +25 -0
- microsoft_agents/activity/teams/message_actions_payload_mention.py +23 -0
- microsoft_agents/activity/teams/message_actions_payload_reaction.py +23 -0
- microsoft_agents/activity/teams/message_actions_payload_user.py +27 -0
- microsoft_agents/activity/teams/messaging_extension_action.py +37 -0
- microsoft_agents/activity/teams/messaging_extension_action_response.py +24 -0
- microsoft_agents/activity/teams/messaging_extension_attachment.py +32 -0
- microsoft_agents/activity/teams/messaging_extension_parameter.py +17 -0
- microsoft_agents/activity/teams/messaging_extension_query.py +27 -0
- microsoft_agents/activity/teams/messaging_extension_query_options.py +17 -0
- microsoft_agents/activity/teams/messaging_extension_response.py +21 -0
- microsoft_agents/activity/teams/messaging_extension_result.py +34 -0
- microsoft_agents/activity/teams/messaging_extension_suggested_action.py +17 -0
- microsoft_agents/activity/teams/notification_info.py +21 -0
- microsoft_agents/activity/teams/o365_connector_card.py +32 -0
- microsoft_agents/activity/teams/o365_connector_card_action_base.py +21 -0
- microsoft_agents/activity/teams/o365_connector_card_action_card.py +30 -0
- microsoft_agents/activity/teams/o365_connector_card_action_query.py +15 -0
- microsoft_agents/activity/teams/o365_connector_card_date_input.py +30 -0
- microsoft_agents/activity/teams/o365_connector_card_fact.py +17 -0
- microsoft_agents/activity/teams/o365_connector_card_http_post.py +25 -0
- microsoft_agents/activity/teams/o365_connector_card_image.py +18 -0
- microsoft_agents/activity/teams/o365_connector_card_input_base.py +28 -0
- microsoft_agents/activity/teams/o365_connector_card_multichoice_input.py +40 -0
- microsoft_agents/activity/teams/o365_connector_card_multichoice_input_choice.py +17 -0
- microsoft_agents/activity/teams/o365_connector_card_open_uri.py +26 -0
- microsoft_agents/activity/teams/o365_connector_card_open_uri_target.py +17 -0
- microsoft_agents/activity/teams/o365_connector_card_section.py +42 -0
- microsoft_agents/activity/teams/o365_connector_card_text_input.py +31 -0
- microsoft_agents/activity/teams/o365_connector_card_view_action.py +25 -0
- microsoft_agents/activity/teams/on_behalf_of.py +23 -0
- microsoft_agents/activity/teams/read_receipt_info.py +47 -0
- microsoft_agents/activity/teams/signin_state_verification_query.py +14 -0
- microsoft_agents/activity/teams/surface.py +18 -0
- microsoft_agents/activity/teams/tab_context.py +14 -0
- microsoft_agents/activity/teams/tab_entity_context.py +15 -0
- microsoft_agents/activity/teams/tab_request.py +22 -0
- microsoft_agents/activity/teams/tab_response.py +16 -0
- microsoft_agents/activity/teams/tab_response_card.py +14 -0
- microsoft_agents/activity/teams/tab_response_cards.py +17 -0
- microsoft_agents/activity/teams/tab_response_payload.py +25 -0
- microsoft_agents/activity/teams/tab_submit.py +23 -0
- microsoft_agents/activity/teams/tab_submit_data.py +18 -0
- microsoft_agents/activity/teams/tab_suggested_actions.py +17 -0
- microsoft_agents/activity/teams/targeted_meeting_notification.py +19 -0
- microsoft_agents/activity/teams/targeted_meeting_notification_value.py +19 -0
- microsoft_agents/activity/teams/task_module_card_response.py +15 -0
- microsoft_agents/activity/teams/task_module_continue_response.py +19 -0
- microsoft_agents/activity/teams/task_module_message_response.py +18 -0
- microsoft_agents/activity/teams/task_module_request.py +25 -0
- microsoft_agents/activity/teams/task_module_request_context.py +15 -0
- microsoft_agents/activity/teams/task_module_response.py +20 -0
- microsoft_agents/activity/teams/task_module_response_base.py +17 -0
- microsoft_agents/activity/teams/task_module_task_info.py +30 -0
- microsoft_agents/activity/teams/team_details.py +29 -0
- microsoft_agents/activity/teams/team_info.py +20 -0
- microsoft_agents/activity/teams/teams_batch_operation_response.py +19 -0
- microsoft_agents/activity/teams/teams_channel_account.py +44 -0
- microsoft_agents/activity/teams/teams_channel_data.py +43 -0
- microsoft_agents/activity/teams/teams_channel_data_settings.py +15 -0
- microsoft_agents/activity/teams/teams_meeting_info.py +14 -0
- microsoft_agents/activity/teams/teams_meeting_member.py +19 -0
- microsoft_agents/activity/teams/teams_meeting_participant.py +24 -0
- microsoft_agents/activity/teams/teams_member.py +14 -0
- microsoft_agents/activity/teams/teams_paged_members_result.py +19 -0
- microsoft_agents/activity/teams/tenant_info.py +14 -0
- microsoft_agents/activity/teams/user_meeting_details.py +17 -0
- microsoft_agents/activity/text_format_types.py +10 -0
- microsoft_agents/activity/text_highlight.py +19 -0
- microsoft_agents/activity/thumbnail_card.py +33 -0
- microsoft_agents/activity/thumbnail_url.py +18 -0
- microsoft_agents/activity/token_exchange_invoke_request.py +24 -0
- microsoft_agents/activity/token_exchange_invoke_response.py +24 -0
- microsoft_agents/activity/token_exchange_resource.py +16 -0
- microsoft_agents/activity/token_exchange_state.py +41 -0
- microsoft_agents/activity/token_or_sign_in_resource_response.py +21 -0
- microsoft_agents/activity/token_post_resource.py +14 -0
- microsoft_agents/activity/token_request.py +19 -0
- microsoft_agents/activity/token_response.py +46 -0
- microsoft_agents/activity/token_status.py +32 -0
- microsoft_agents/activity/transcript.py +16 -0
- microsoft_agents/activity/turn_context_protocol.py +68 -0
- microsoft_agents/activity/video_card.py +57 -0
- microsoft_agents_activity-0.7.0.dev0.dist-info/METADATA +173 -0
- microsoft_agents_activity-0.7.0.dev0.dist-info/RECORD +208 -0
- microsoft_agents_activity-0.7.0.dev0.dist-info/WHEEL +5 -0
- microsoft_agents_activity-0.7.0.dev0.dist-info/licenses/LICENSE +21 -0
- microsoft_agents_activity-0.7.0.dev0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,787 @@
|
|
|
1
|
+
# Copyright (c) Microsoft Corporation. All rights reserved.
|
|
2
|
+
# Licensed under the MIT License.
|
|
3
|
+
|
|
4
|
+
from __future__ import annotations
|
|
5
|
+
|
|
6
|
+
import logging
|
|
7
|
+
from copy import copy
|
|
8
|
+
from datetime import datetime, timezone
|
|
9
|
+
from typing import Optional, Any
|
|
10
|
+
|
|
11
|
+
from pydantic import (
|
|
12
|
+
Field,
|
|
13
|
+
SerializeAsAny,
|
|
14
|
+
model_serializer,
|
|
15
|
+
model_validator,
|
|
16
|
+
SerializerFunctionWrapHandler,
|
|
17
|
+
ModelWrapValidatorHandler,
|
|
18
|
+
computed_field,
|
|
19
|
+
ValidationError,
|
|
20
|
+
)
|
|
21
|
+
|
|
22
|
+
from .activity_types import ActivityTypes
|
|
23
|
+
from .channel_account import ChannelAccount
|
|
24
|
+
from .conversation_account import ConversationAccount
|
|
25
|
+
from .message_reaction import MessageReaction
|
|
26
|
+
from .resource_response import ResourceResponse
|
|
27
|
+
from .suggested_actions import SuggestedActions
|
|
28
|
+
from .attachment import Attachment
|
|
29
|
+
from .entity import (
|
|
30
|
+
Entity,
|
|
31
|
+
EntityTypes,
|
|
32
|
+
Mention,
|
|
33
|
+
AIEntity,
|
|
34
|
+
ClientCitation,
|
|
35
|
+
ProductInfo,
|
|
36
|
+
SensitivityUsageInfo,
|
|
37
|
+
)
|
|
38
|
+
from .conversation_reference import ConversationReference
|
|
39
|
+
from .text_highlight import TextHighlight
|
|
40
|
+
from .semantic_action import SemanticAction
|
|
41
|
+
from .agents_model import AgentsModel
|
|
42
|
+
from .role_types import RoleTypes
|
|
43
|
+
from ._channel_id_field_mixin import _ChannelIdFieldMixin
|
|
44
|
+
from .channel_id import ChannelId
|
|
45
|
+
from ._model_utils import pick_model, SkipNone
|
|
46
|
+
from ._type_aliases import NonEmptyString
|
|
47
|
+
from microsoft_agents.activity.errors import activity_errors
|
|
48
|
+
|
|
49
|
+
logger = logging.getLogger(__name__)
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
# TODO: A2A Agent 2 is responding with None as id, had to mark it as optional (investigate)
|
|
53
|
+
class Activity(AgentsModel, _ChannelIdFieldMixin):
|
|
54
|
+
"""An Activity is the basic communication type for the protocol.
|
|
55
|
+
|
|
56
|
+
:param type: Contains the activity type. Possible values include:
|
|
57
|
+
'message', 'contactRelationUpdate', 'conversationUpdate', 'typing',
|
|
58
|
+
'endOfConversation', 'event', 'invoke', 'deleteUserData', 'messageUpdate',
|
|
59
|
+
'messageDelete', 'installationUpdate', 'messageReaction', 'suggestion',
|
|
60
|
+
'trace', 'handoff'
|
|
61
|
+
:type type: str or ~microsoft_agents.activity.ActivityTypes
|
|
62
|
+
:param id: Contains an ID that uniquely identifies the activity on the channel.
|
|
63
|
+
:type id: str
|
|
64
|
+
:param timestamp: Contains the date and time that the message was sent, in UTC, expressed in ISO-8601 format.
|
|
65
|
+
:type timestamp: datetime
|
|
66
|
+
:param local_timestamp: Contains the local date and time of the message expressed in ISO-8601 format.
|
|
67
|
+
For example, 2016-09-23T13:07:49.4714686-07:00.
|
|
68
|
+
:type local_timestamp: datetime
|
|
69
|
+
:param local_timezone: Contains the name of the local timezone of the message, expressed in IANA Time Zone database format.
|
|
70
|
+
For example, America/Los_Angeles.
|
|
71
|
+
:type local_timezone: str
|
|
72
|
+
:param service_url: Contains the URL that specifies the channel's service endpoint. Set by the channel.
|
|
73
|
+
:type service_url: str
|
|
74
|
+
:param channel_id: Contains an ID that uniquely identifies the channel (and possibly the sub-channel). Set by the channel.
|
|
75
|
+
:type channel_id: ~microsoft_agents.activity.ChannelId
|
|
76
|
+
:param from_property: Identifies the sender of the message.
|
|
77
|
+
:type from_property: ~microsoft_agents.activity.ChannelAccount
|
|
78
|
+
:param conversation: Identifies the conversation to which the activity belongs.
|
|
79
|
+
:type conversation: ~microsoft_agents.activity.ConversationAccount
|
|
80
|
+
:param recipient: Identifies the recipient of the message.
|
|
81
|
+
:type recipient: ~microsoft_agents.activity.ChannelAccount
|
|
82
|
+
:param text_format: Format of text fields Default:markdown. Possible values include: 'markdown', 'plain', 'xml'
|
|
83
|
+
:type text_format: str or ~microsoft_agents.activity.TextFormatTypes
|
|
84
|
+
:param attachment_layout: The layout hint for multiple attachments. Default: list. Possible values include: 'list', 'carousel'
|
|
85
|
+
:type attachment_layout: str or ~microsoft_agents.activity.AttachmentLayoutTypes
|
|
86
|
+
:param members_added: The collection of members added to the conversation.
|
|
87
|
+
:type members_added: list[~microsoft_agents.activity.ChannelAccount]
|
|
88
|
+
:param members_removed: The collection of members removed from the conversation.
|
|
89
|
+
:type members_removed: list[~microsoft_agents.activity.ChannelAccount]
|
|
90
|
+
:param reactions_added: The collection of reactions added to the conversation.
|
|
91
|
+
:type reactions_added: list[~microsoft_agents.activity.MessageReaction]
|
|
92
|
+
:param reactions_removed: The collection of reactions removed from the conversation.
|
|
93
|
+
:type reactions_removed: list[~microsoft_agents.activity.MessageReaction]
|
|
94
|
+
:param topic_name: The updated topic name of the conversation.
|
|
95
|
+
:type topic_name: str
|
|
96
|
+
:param history_disclosed: Indicates whether the prior history of the channel is disclosed.
|
|
97
|
+
:type history_disclosed: bool
|
|
98
|
+
:param locale: A locale name for the contents of the text field. The locale name is a combination of an ISO 639 two- or three-letter
|
|
99
|
+
culture code associated with a language and an ISO 3166 two-letter subculture code associated with a country or region.
|
|
100
|
+
The locale name can also correspond to a valid BCP-47 language tag.
|
|
101
|
+
:type locale: str
|
|
102
|
+
:param text: The text content of the message.
|
|
103
|
+
:type text: str
|
|
104
|
+
:param speak: The text to speak.
|
|
105
|
+
:type speak: str
|
|
106
|
+
:param input_hint: Indicates whether your agent is accepting, expecting, or ignoring user input after the message is delivered to the client.
|
|
107
|
+
Possible values include: 'acceptingInput', 'ignoringInput', 'expectingInput'
|
|
108
|
+
:type input_hint: str or ~microsoft_agents.activity.InputHints
|
|
109
|
+
:param summary: The text to display if the channel cannot render cards.
|
|
110
|
+
:type summary: str
|
|
111
|
+
:param suggested_actions: The suggested actions for the activity.
|
|
112
|
+
:type suggested_actions: ~microsoft_agents.activity.SuggestedActions
|
|
113
|
+
:param attachments: Attachments
|
|
114
|
+
:type attachments: list[~microsoft_agents.activity.Attachment]
|
|
115
|
+
:param entities: Represents the entities that were mentioned in the message.
|
|
116
|
+
:type entities: list[~microsoft_agents.activity.Entity]
|
|
117
|
+
:param channel_data: Contains channel-specific content.
|
|
118
|
+
:type channel_data: object
|
|
119
|
+
:param action: Indicates whether the recipient of a contactRelationUpdate was added or removed from the sender's contact list.
|
|
120
|
+
:type action: str
|
|
121
|
+
:param reply_to_id: Contains the ID of the message to which this message is a reply.
|
|
122
|
+
:type reply_to_id: str
|
|
123
|
+
:param label: A descriptive label for the activity.
|
|
124
|
+
:type label: str
|
|
125
|
+
:param value_type: The type of the activity's value object.
|
|
126
|
+
:type value_type: str
|
|
127
|
+
:param value: A value that is associated with the activity.
|
|
128
|
+
:type value: object
|
|
129
|
+
:param name: The name of the operation associated with an invoke or event activity.
|
|
130
|
+
:type name: str
|
|
131
|
+
:param relates_to: A reference to another conversation or activity.
|
|
132
|
+
:type relates_to: ~microsoft_agents.activity.ConversationReference
|
|
133
|
+
:param code: The a code for endOfConversation activities that indicates why the conversation ended. Possible values include: 'unknown',
|
|
134
|
+
'completedSuccessfully', 'userCancelled', 'botTimedOut', 'botIssuedInvalidMessage', 'channelFailed'
|
|
135
|
+
:type code: str or ~microsoft_agents.activity.EndOfConversationCodes
|
|
136
|
+
:param expiration: The time at which the activity should be considered to be "expired" and should not be presented to the recipient.
|
|
137
|
+
:type expiration: datetime
|
|
138
|
+
:param importance: The importance of the activity. Possible values include: 'low', 'normal', 'high'
|
|
139
|
+
:type importance: str or ~microsoft_agents.activity.ActivityImportance
|
|
140
|
+
:param delivery_mode: A delivery hint to signal to the recipient alternate delivery paths for the activity.
|
|
141
|
+
The default delivery mode is "default". Possible values include: 'normal', 'notification', 'expectReplies', 'ephemeral'
|
|
142
|
+
:type delivery_mode: str or ~microsoft_agents.activity.DeliveryModes
|
|
143
|
+
:param listen_for: List of phrases and references that speech and language priming systems should listen for
|
|
144
|
+
:type listen_for: list[str]
|
|
145
|
+
:param text_highlights: The collection of text fragments to highlight when the activity contains a ReplyToId value.
|
|
146
|
+
:type text_highlights: list[~microsoft_agents.activity.TextHighlight]
|
|
147
|
+
:param semantic_action: An optional programmatic action accompanying this request
|
|
148
|
+
:type semantic_action: ~microsoft_agents.activity.SemanticAction
|
|
149
|
+
:param caller_id: A string containing an IRI identifying the caller of an agent. This field is not intended to be transmitted over the wire,
|
|
150
|
+
but is instead populated by agents and clients based on cryptographically verifiable data that asserts the identity of the callers (e.g. tokens).
|
|
151
|
+
:type caller_id: str
|
|
152
|
+
"""
|
|
153
|
+
|
|
154
|
+
type: NonEmptyString
|
|
155
|
+
id: Optional[NonEmptyString] = None
|
|
156
|
+
timestamp: datetime = None
|
|
157
|
+
local_timestamp: datetime = None
|
|
158
|
+
local_timezone: NonEmptyString = None
|
|
159
|
+
service_url: NonEmptyString = None
|
|
160
|
+
from_property: ChannelAccount = Field(None, alias="from")
|
|
161
|
+
conversation: ConversationAccount = None
|
|
162
|
+
recipient: ChannelAccount = None
|
|
163
|
+
text_format: NonEmptyString = None
|
|
164
|
+
attachment_layout: NonEmptyString = None
|
|
165
|
+
members_added: list[ChannelAccount] = None
|
|
166
|
+
members_removed: list[ChannelAccount] = None
|
|
167
|
+
reactions_added: list[MessageReaction] = None
|
|
168
|
+
reactions_removed: list[MessageReaction] = None
|
|
169
|
+
topic_name: NonEmptyString = None
|
|
170
|
+
history_disclosed: bool = None
|
|
171
|
+
locale: NonEmptyString = None
|
|
172
|
+
text: str = None
|
|
173
|
+
speak: str = None
|
|
174
|
+
input_hint: NonEmptyString = None
|
|
175
|
+
summary: NonEmptyString = None
|
|
176
|
+
suggested_actions: SuggestedActions = None
|
|
177
|
+
attachments: list[Attachment] = None
|
|
178
|
+
entities: list[SerializeAsAny[Entity]] = None
|
|
179
|
+
channel_data: object = None
|
|
180
|
+
action: NonEmptyString = None
|
|
181
|
+
reply_to_id: NonEmptyString = None
|
|
182
|
+
label: NonEmptyString = None
|
|
183
|
+
value_type: NonEmptyString = None
|
|
184
|
+
value: object = None
|
|
185
|
+
name: NonEmptyString = None
|
|
186
|
+
relates_to: ConversationReference = None
|
|
187
|
+
code: NonEmptyString = None
|
|
188
|
+
expiration: datetime = None
|
|
189
|
+
importance: NonEmptyString = None
|
|
190
|
+
delivery_mode: NonEmptyString = None
|
|
191
|
+
listen_for: list[NonEmptyString] = None
|
|
192
|
+
text_highlights: list[TextHighlight] = None
|
|
193
|
+
semantic_action: SemanticAction = None
|
|
194
|
+
caller_id: NonEmptyString = None
|
|
195
|
+
|
|
196
|
+
@model_validator(mode="wrap")
|
|
197
|
+
@classmethod
|
|
198
|
+
def _validate_channel_id(
|
|
199
|
+
cls, data: Any, handler: ModelWrapValidatorHandler[Activity]
|
|
200
|
+
) -> Activity:
|
|
201
|
+
"""Validate the Activity, ensuring consistency between channel_id.sub_channel and productInfo entity.
|
|
202
|
+
|
|
203
|
+
:param data: The input data to validate.
|
|
204
|
+
:param handler: The validation handler provided by Pydantic.
|
|
205
|
+
:return: The validated Activity instance.
|
|
206
|
+
"""
|
|
207
|
+
try:
|
|
208
|
+
# run Pydantic's standard validation first
|
|
209
|
+
activity = handler(data)
|
|
210
|
+
|
|
211
|
+
# needed to assign to a computed field
|
|
212
|
+
# needed because we override the mixin validator
|
|
213
|
+
activity._set_validated_channel_id(data)
|
|
214
|
+
|
|
215
|
+
# sync sub_channel with productInfo entity
|
|
216
|
+
product_info = activity.get_product_info_entity()
|
|
217
|
+
if product_info and activity.channel_id:
|
|
218
|
+
if (
|
|
219
|
+
activity.channel_id.sub_channel
|
|
220
|
+
and activity.channel_id.sub_channel != product_info.id
|
|
221
|
+
):
|
|
222
|
+
raise Exception(str(activity_errors.ChannelIdProductInfoConflict))
|
|
223
|
+
activity.channel_id = ChannelId(
|
|
224
|
+
channel=activity.channel_id.channel,
|
|
225
|
+
sub_channel=product_info.id,
|
|
226
|
+
)
|
|
227
|
+
|
|
228
|
+
return activity
|
|
229
|
+
except ValidationError as exc:
|
|
230
|
+
logger.error("Validation error for Activity: %s", exc, exc_info=True)
|
|
231
|
+
raise
|
|
232
|
+
|
|
233
|
+
@model_serializer(mode="wrap")
|
|
234
|
+
def _serialize_sub_channel_data(
|
|
235
|
+
self, handler: SerializerFunctionWrapHandler
|
|
236
|
+
) -> dict[str, object]:
|
|
237
|
+
"""Serialize the Activity, ensuring consistency between channel_id.sub_channel and productInfo entity.
|
|
238
|
+
|
|
239
|
+
:param handler: The serialization handler provided by Pydantic.
|
|
240
|
+
:return: A dictionary representing the serialized Activity.
|
|
241
|
+
"""
|
|
242
|
+
|
|
243
|
+
# run Pydantic's standard serialization first
|
|
244
|
+
serialized = handler(self)
|
|
245
|
+
if not self: # serialization can be called with None
|
|
246
|
+
return serialized
|
|
247
|
+
|
|
248
|
+
# find the ProductInfo entity
|
|
249
|
+
product_info = None
|
|
250
|
+
for i, entity in enumerate(serialized.get("entities") or []):
|
|
251
|
+
if entity.get("type", "") == EntityTypes.PRODUCT_INFO:
|
|
252
|
+
product_info = entity
|
|
253
|
+
break
|
|
254
|
+
|
|
255
|
+
# self.channel_id is the source of truth for serialization
|
|
256
|
+
if self.channel_id and self.channel_id.sub_channel:
|
|
257
|
+
if product_info and product_info.get("id") != self.channel_id.sub_channel:
|
|
258
|
+
raise Exception(str(activity_errors.ChannelIdProductInfoConflict))
|
|
259
|
+
elif not product_info:
|
|
260
|
+
if not serialized.get("entities"):
|
|
261
|
+
serialized["entities"] = []
|
|
262
|
+
serialized["entities"].append(
|
|
263
|
+
{
|
|
264
|
+
"type": EntityTypes.PRODUCT_INFO,
|
|
265
|
+
"id": self.channel_id.sub_channel,
|
|
266
|
+
}
|
|
267
|
+
)
|
|
268
|
+
|
|
269
|
+
# simply serialized channelId value in Activity and relatesTo
|
|
270
|
+
if "channelId" in serialized:
|
|
271
|
+
serialized["channelId"] = self.channel_id.channel
|
|
272
|
+
elif "channel_id" in serialized:
|
|
273
|
+
serialized["channel_id"] = self.channel_id.channel
|
|
274
|
+
|
|
275
|
+
elif product_info: # remove productInfo entity if sub_channel is not set
|
|
276
|
+
del serialized["entities"][i]
|
|
277
|
+
if not serialized["entities"]: # after removal above, list may be empty
|
|
278
|
+
del serialized["entities"]
|
|
279
|
+
|
|
280
|
+
# necessary due to computed_field serialization
|
|
281
|
+
self._remove_serialized_unset_channel_id(serialized)
|
|
282
|
+
|
|
283
|
+
return serialized
|
|
284
|
+
|
|
285
|
+
def apply_conversation_reference(
|
|
286
|
+
self, reference: ConversationReference, is_incoming: bool = False
|
|
287
|
+
):
|
|
288
|
+
"""
|
|
289
|
+
Updates this activity with the delivery information from an existing ConversationReference.
|
|
290
|
+
|
|
291
|
+
:param reference: The existing conversation reference.
|
|
292
|
+
:param is_incoming: Optional, True to treat the activity as an incoming activity, where the agent is the recipient; otherwise, False.
|
|
293
|
+
Default is False, and the activity will show the agent as the sender.
|
|
294
|
+
|
|
295
|
+
:returns: This activity, updated with the delivery information.
|
|
296
|
+
|
|
297
|
+
.. remarks::
|
|
298
|
+
Call GetConversationReference on an incoming activity to get a conversation reference that you can then use to update an
|
|
299
|
+
outgoing activity with the correct delivery information.
|
|
300
|
+
"""
|
|
301
|
+
self.channel_id = reference.channel_id
|
|
302
|
+
self.service_url = reference.service_url
|
|
303
|
+
self.conversation = reference.conversation
|
|
304
|
+
|
|
305
|
+
if reference.locale is not None:
|
|
306
|
+
self.locale = reference.locale
|
|
307
|
+
|
|
308
|
+
if is_incoming:
|
|
309
|
+
self.from_property = reference.user
|
|
310
|
+
self.recipient = reference.agent
|
|
311
|
+
|
|
312
|
+
if reference.activity_id is not None:
|
|
313
|
+
self.id = reference.activity_id
|
|
314
|
+
else:
|
|
315
|
+
self.from_property = reference.agent
|
|
316
|
+
self.recipient = reference.user
|
|
317
|
+
|
|
318
|
+
if reference.activity_id is not None:
|
|
319
|
+
self.reply_to_id = reference.activity_id
|
|
320
|
+
|
|
321
|
+
return self
|
|
322
|
+
|
|
323
|
+
def as_contact_relation_update_activity(self):
|
|
324
|
+
"""
|
|
325
|
+
Returns this activity as a ContactRelationUpdateActivity object; or None, if this is not that type of activity.
|
|
326
|
+
|
|
327
|
+
:returns: This activity as a message activity; or None.
|
|
328
|
+
"""
|
|
329
|
+
return (
|
|
330
|
+
self if self.__is_activity(ActivityTypes.contact_relation_update) else None
|
|
331
|
+
)
|
|
332
|
+
|
|
333
|
+
def as_conversation_update_activity(self):
|
|
334
|
+
"""
|
|
335
|
+
Returns this activity as a ConversationUpdateActivity object; or None, if this is not that type of activity.
|
|
336
|
+
|
|
337
|
+
:returns: This activity as a conversation update activity; or None.
|
|
338
|
+
"""
|
|
339
|
+
return self if self.__is_activity(ActivityTypes.conversation_update) else None
|
|
340
|
+
|
|
341
|
+
def as_end_of_conversation_activity(self):
|
|
342
|
+
"""
|
|
343
|
+
Returns this activity as an EndOfConversationActivity object; or None, if this is not that type of activity.
|
|
344
|
+
|
|
345
|
+
:returns: This activity as an end of conversation activity; or None.
|
|
346
|
+
"""
|
|
347
|
+
return self if self.__is_activity(ActivityTypes.end_of_conversation) else None
|
|
348
|
+
|
|
349
|
+
def as_event_activity(self):
|
|
350
|
+
"""
|
|
351
|
+
Returns this activity as an EventActivity object; or None, if this is not that type of activity.
|
|
352
|
+
|
|
353
|
+
:returns: This activity as an event activity; or None.
|
|
354
|
+
"""
|
|
355
|
+
return self if self.__is_activity(ActivityTypes.event) else None
|
|
356
|
+
|
|
357
|
+
def as_handoff_activity(self):
|
|
358
|
+
"""
|
|
359
|
+
Returns this activity as a HandoffActivity object; or None, if this is not that type of activity.
|
|
360
|
+
|
|
361
|
+
:returns: This activity as a handoff activity; or None.
|
|
362
|
+
"""
|
|
363
|
+
return self if self.__is_activity(ActivityTypes.handoff) else None
|
|
364
|
+
|
|
365
|
+
def as_installation_update_activity(self):
|
|
366
|
+
"""
|
|
367
|
+
Returns this activity as an InstallationUpdateActivity object; or None, if this is not that type of activity.
|
|
368
|
+
|
|
369
|
+
:returns: This activity as an installation update activity; or None.
|
|
370
|
+
"""
|
|
371
|
+
return self if self.__is_activity(ActivityTypes.installation_update) else None
|
|
372
|
+
|
|
373
|
+
def as_invoke_activity(self):
|
|
374
|
+
"""
|
|
375
|
+
Returns this activity as an InvokeActivity object; or None, if this is not that type of activity.
|
|
376
|
+
|
|
377
|
+
:returns: This activity as an invoke activity; or None.
|
|
378
|
+
"""
|
|
379
|
+
return self if self.__is_activity(ActivityTypes.invoke) else None
|
|
380
|
+
|
|
381
|
+
def as_message_activity(self):
|
|
382
|
+
"""
|
|
383
|
+
Returns this activity as a MessageActivity object; or None, if this is not that type of activity.
|
|
384
|
+
|
|
385
|
+
:returns: This activity as a message activity; or None.
|
|
386
|
+
"""
|
|
387
|
+
return self if self.__is_activity(ActivityTypes.message) else None
|
|
388
|
+
|
|
389
|
+
def as_message_delete_activity(self):
|
|
390
|
+
"""
|
|
391
|
+
Returns this activity as a MessageDeleteActivity object; or None, if this is not that type of activity.
|
|
392
|
+
|
|
393
|
+
:returns: This activity as a message delete request; or None.
|
|
394
|
+
"""
|
|
395
|
+
return self if self.__is_activity(ActivityTypes.message_delete) else None
|
|
396
|
+
|
|
397
|
+
def as_message_reaction_activity(self):
|
|
398
|
+
"""
|
|
399
|
+
Returns this activity as a MessageReactionActivity object; or None, if this is not that type of activity.
|
|
400
|
+
|
|
401
|
+
:return: This activity as a message reaction activity; or None.
|
|
402
|
+
"""
|
|
403
|
+
return self if self.__is_activity(ActivityTypes.message_reaction) else None
|
|
404
|
+
|
|
405
|
+
def as_message_update_activity(self):
|
|
406
|
+
"""
|
|
407
|
+
Returns this activity as an MessageUpdateActivity object; or None, if this is not that type of activity.
|
|
408
|
+
|
|
409
|
+
:returns: This activity as a message update request; or None.
|
|
410
|
+
"""
|
|
411
|
+
return self if self.__is_activity(ActivityTypes.message_update) else None
|
|
412
|
+
|
|
413
|
+
def as_suggestion_activity(self):
|
|
414
|
+
"""
|
|
415
|
+
Returns this activity as a SuggestionActivity object; or None, if this is not that type of activity.
|
|
416
|
+
|
|
417
|
+
:returns: This activity as a suggestion activity; or None.
|
|
418
|
+
"""
|
|
419
|
+
return self if self.__is_activity(ActivityTypes.suggestion) else None
|
|
420
|
+
|
|
421
|
+
def as_trace_activity(self):
|
|
422
|
+
"""
|
|
423
|
+
Returns this activity as a TraceActivity object; or None, if this is not that type of activity.
|
|
424
|
+
|
|
425
|
+
:returns: This activity as a trace activity; or None.
|
|
426
|
+
"""
|
|
427
|
+
return self if self.__is_activity(ActivityTypes.trace) else None
|
|
428
|
+
|
|
429
|
+
def as_typing_activity(self):
|
|
430
|
+
"""
|
|
431
|
+
Returns this activity as a TypingActivity object; or null, if this is not that type of activity.
|
|
432
|
+
|
|
433
|
+
:returns: This activity as a typing activity; or null.
|
|
434
|
+
"""
|
|
435
|
+
return self if self.__is_activity(ActivityTypes.typing) else None
|
|
436
|
+
|
|
437
|
+
@staticmethod
|
|
438
|
+
def create_contact_relation_update_activity():
|
|
439
|
+
"""
|
|
440
|
+
Creates an instance of the :class:`Activity` class as a ContactRelationUpdateActivity object.
|
|
441
|
+
|
|
442
|
+
:returns: The new contact relation update activity.
|
|
443
|
+
"""
|
|
444
|
+
return Activity(type=ActivityTypes.contact_relation_update)
|
|
445
|
+
|
|
446
|
+
@staticmethod
|
|
447
|
+
def create_conversation_update_activity():
|
|
448
|
+
"""
|
|
449
|
+
Creates an instance of the :class:`Activity` class as a ConversationUpdateActivity object.
|
|
450
|
+
|
|
451
|
+
:returns: The new conversation update activity.
|
|
452
|
+
"""
|
|
453
|
+
return Activity(type=ActivityTypes.conversation_update)
|
|
454
|
+
|
|
455
|
+
@staticmethod
|
|
456
|
+
def create_end_of_conversation_activity():
|
|
457
|
+
"""
|
|
458
|
+
Creates an instance of the :class:`Activity` class as an EndOfConversationActivity object.
|
|
459
|
+
|
|
460
|
+
:returns: The new end of conversation activity.
|
|
461
|
+
"""
|
|
462
|
+
return Activity(type=ActivityTypes.end_of_conversation)
|
|
463
|
+
|
|
464
|
+
@staticmethod
|
|
465
|
+
def create_event_activity():
|
|
466
|
+
"""
|
|
467
|
+
Creates an instance of the :class:`Activity` class as an EventActivity object.
|
|
468
|
+
|
|
469
|
+
:returns: The new event activity.
|
|
470
|
+
"""
|
|
471
|
+
return Activity(type=ActivityTypes.event)
|
|
472
|
+
|
|
473
|
+
@staticmethod
|
|
474
|
+
def create_handoff_activity():
|
|
475
|
+
"""
|
|
476
|
+
Creates an instance of the :class:`Activity` class as a HandoffActivity object.
|
|
477
|
+
|
|
478
|
+
:returns: The new handoff activity.
|
|
479
|
+
"""
|
|
480
|
+
return Activity(type=ActivityTypes.handoff)
|
|
481
|
+
|
|
482
|
+
@staticmethod
|
|
483
|
+
def create_invoke_activity():
|
|
484
|
+
"""
|
|
485
|
+
Creates an instance of the :class:`Activity` class as an InvokeActivity object.
|
|
486
|
+
|
|
487
|
+
:returns: The new invoke activity.
|
|
488
|
+
"""
|
|
489
|
+
return Activity(type=ActivityTypes.invoke)
|
|
490
|
+
|
|
491
|
+
@staticmethod
|
|
492
|
+
def create_message_activity():
|
|
493
|
+
"""
|
|
494
|
+
Creates an instance of the :class:`Activity` class as a MessageActivity object.
|
|
495
|
+
|
|
496
|
+
:returns: The new message activity.
|
|
497
|
+
"""
|
|
498
|
+
return Activity(type=ActivityTypes.message)
|
|
499
|
+
|
|
500
|
+
def create_reply(self, text: str = None, locale: str = None):
|
|
501
|
+
"""
|
|
502
|
+
Creates a new message activity as a response to this activity.
|
|
503
|
+
|
|
504
|
+
:param text: The text of the reply.
|
|
505
|
+
:param locale: The language code for the text.
|
|
506
|
+
|
|
507
|
+
:returns: The new message activity.
|
|
508
|
+
|
|
509
|
+
.. remarks::
|
|
510
|
+
The new activity sets up routing information based on this activity.
|
|
511
|
+
"""
|
|
512
|
+
return pick_model(
|
|
513
|
+
Activity,
|
|
514
|
+
type=ActivityTypes.message,
|
|
515
|
+
timestamp=datetime.now(timezone.utc),
|
|
516
|
+
from_property=SkipNone(
|
|
517
|
+
ChannelAccount.pick_properties(self.recipient, ["id", "name"])
|
|
518
|
+
),
|
|
519
|
+
recipient=SkipNone(
|
|
520
|
+
ChannelAccount.pick_properties(self.from_property, ["id", "name"])
|
|
521
|
+
),
|
|
522
|
+
reply_to_id=(
|
|
523
|
+
SkipNone(self.id)
|
|
524
|
+
if type != ActivityTypes.conversation_update
|
|
525
|
+
or self.channel_id not in ["directline", "webchat"]
|
|
526
|
+
else None
|
|
527
|
+
),
|
|
528
|
+
service_url=self.service_url,
|
|
529
|
+
channel_id=self.channel_id,
|
|
530
|
+
conversation=SkipNone(
|
|
531
|
+
ConversationAccount.pick_properties(
|
|
532
|
+
self.conversation, ["is_group", "id", "name"]
|
|
533
|
+
)
|
|
534
|
+
),
|
|
535
|
+
text=text if text else "",
|
|
536
|
+
locale=locale if locale else SkipNone(self.locale),
|
|
537
|
+
attachments=[],
|
|
538
|
+
entities=[],
|
|
539
|
+
)
|
|
540
|
+
|
|
541
|
+
def create_trace(
|
|
542
|
+
self, name: str, value: object = None, value_type: str = None, label: str = None
|
|
543
|
+
):
|
|
544
|
+
"""
|
|
545
|
+
Creates a new trace activity based on this activity.
|
|
546
|
+
|
|
547
|
+
:param name: The name of the trace operation to create.
|
|
548
|
+
:param value: Optional, the content for this trace operation.
|
|
549
|
+
:param value_type: Optional, identifier for the format of the value. Default is the name of type of the value.
|
|
550
|
+
:param label: Optional, a descriptive label for this trace operation.
|
|
551
|
+
|
|
552
|
+
:returns: The new trace activity.
|
|
553
|
+
"""
|
|
554
|
+
if not value_type and value:
|
|
555
|
+
value_type = type(value).__name__
|
|
556
|
+
|
|
557
|
+
return pick_model(
|
|
558
|
+
Activity,
|
|
559
|
+
type=ActivityTypes.trace,
|
|
560
|
+
timestamp=datetime.now(timezone.utc),
|
|
561
|
+
from_property=SkipNone(
|
|
562
|
+
ChannelAccount.pick_properties(self.recipient, ["id", "name"])
|
|
563
|
+
),
|
|
564
|
+
recipient=SkipNone(
|
|
565
|
+
ChannelAccount.pick_properties(self.from_property, ["id", "name"])
|
|
566
|
+
),
|
|
567
|
+
reply_to_id=(
|
|
568
|
+
SkipNone(self.id) # preserve unset
|
|
569
|
+
if type != ActivityTypes.conversation_update
|
|
570
|
+
or self.channel_id not in ["directline", "webchat"]
|
|
571
|
+
else None
|
|
572
|
+
),
|
|
573
|
+
service_url=self.service_url,
|
|
574
|
+
channel_id=self.channel_id,
|
|
575
|
+
conversation=SkipNone(
|
|
576
|
+
ConversationAccount.pick_properties(
|
|
577
|
+
self.conversation, ["is_group", "id", "name"]
|
|
578
|
+
)
|
|
579
|
+
),
|
|
580
|
+
name=SkipNone(name),
|
|
581
|
+
label=SkipNone(label),
|
|
582
|
+
value_type=SkipNone(value_type),
|
|
583
|
+
value=SkipNone(value),
|
|
584
|
+
).as_trace_activity()
|
|
585
|
+
|
|
586
|
+
@staticmethod
|
|
587
|
+
def create_trace_activity(
|
|
588
|
+
name: str, value: object = None, value_type: str = None, label: str = None
|
|
589
|
+
):
|
|
590
|
+
"""
|
|
591
|
+
Creates an instance of the :class:`Activity` class as a TraceActivity object.
|
|
592
|
+
|
|
593
|
+
:param name: The name of the trace operation to create.
|
|
594
|
+
:param value: Optional, the content for this trace operation.
|
|
595
|
+
:param value_type: Optional, identifier for the format of the value. Default is the name of type of the value.
|
|
596
|
+
:param label: Optional, a descriptive label for this trace operation.
|
|
597
|
+
|
|
598
|
+
:returns: The new trace activity.
|
|
599
|
+
"""
|
|
600
|
+
if not value_type and value:
|
|
601
|
+
value_type = type(value).__name__
|
|
602
|
+
|
|
603
|
+
return pick_model(
|
|
604
|
+
Activity,
|
|
605
|
+
type=ActivityTypes.trace,
|
|
606
|
+
name=name,
|
|
607
|
+
label=SkipNone(label),
|
|
608
|
+
value_type=SkipNone(value_type),
|
|
609
|
+
value=SkipNone(value),
|
|
610
|
+
)
|
|
611
|
+
|
|
612
|
+
@staticmethod
|
|
613
|
+
def create_typing_activity() -> "Activity":
|
|
614
|
+
"""
|
|
615
|
+
Creates an instance of the :class:`Activity` class as a TypingActivity object.
|
|
616
|
+
|
|
617
|
+
:returns: The new typing activity.
|
|
618
|
+
"""
|
|
619
|
+
return Activity(type=ActivityTypes.typing)
|
|
620
|
+
|
|
621
|
+
def get_conversation_reference(self) -> ConversationReference:
|
|
622
|
+
"""
|
|
623
|
+
Creates a ConversationReference based on this activity.
|
|
624
|
+
|
|
625
|
+
:returns: A conversation reference for the conversation that contains this activity.
|
|
626
|
+
"""
|
|
627
|
+
return pick_model(
|
|
628
|
+
ConversationReference,
|
|
629
|
+
activity_id=(
|
|
630
|
+
SkipNone(self.id)
|
|
631
|
+
if self.type != ActivityTypes.conversation_update
|
|
632
|
+
or self.channel_id not in ["directline", "webchat"]
|
|
633
|
+
else None
|
|
634
|
+
),
|
|
635
|
+
user=copy(self.from_property),
|
|
636
|
+
agent=copy(self.recipient),
|
|
637
|
+
conversation=copy(self.conversation),
|
|
638
|
+
channel_id=self.channel_id,
|
|
639
|
+
locale=self.locale,
|
|
640
|
+
service_url=self.service_url,
|
|
641
|
+
)
|
|
642
|
+
|
|
643
|
+
def get_product_info_entity(self) -> Optional[ProductInfo]:
|
|
644
|
+
if not self.entities:
|
|
645
|
+
return None
|
|
646
|
+
target = EntityTypes.PRODUCT_INFO.lower()
|
|
647
|
+
# validated entities can be Entity, and that prevents us from
|
|
648
|
+
# making assumptions about the casing of the 'type' attribute
|
|
649
|
+
return next(filter(lambda e: e.type.lower() == target, self.entities), None)
|
|
650
|
+
|
|
651
|
+
def get_mentions(self) -> list[Mention]:
|
|
652
|
+
"""
|
|
653
|
+
Resolves the mentions from the entities of this activity.
|
|
654
|
+
|
|
655
|
+
:returns: The array of mentions; or an empty array, if none are found.
|
|
656
|
+
|
|
657
|
+
.. remarks::
|
|
658
|
+
This method is defined on the :class:`Activity` class, but is only intended for use with a message activity,
|
|
659
|
+
where the activity Activity.Type is set to ActivityTypes.Message.
|
|
660
|
+
"""
|
|
661
|
+
if not self.entities:
|
|
662
|
+
return []
|
|
663
|
+
return [x for x in self.entities if x.type.lower() == EntityTypes.MENTION]
|
|
664
|
+
|
|
665
|
+
def get_reply_conversation_reference(
|
|
666
|
+
self, reply: ResourceResponse
|
|
667
|
+
) -> ConversationReference:
|
|
668
|
+
"""
|
|
669
|
+
Create a ConversationReference based on this Activity's Conversation info and the ResourceResponse from sending an activity.
|
|
670
|
+
|
|
671
|
+
:param reply: ResourceResponse returned from send_activity.
|
|
672
|
+
|
|
673
|
+
:return: A ConversationReference that can be stored and used later to delete or update the activity.
|
|
674
|
+
"""
|
|
675
|
+
reference = self.get_conversation_reference()
|
|
676
|
+
reference.activity_id = reply.id
|
|
677
|
+
return reference
|
|
678
|
+
|
|
679
|
+
def has_content(self) -> bool:
|
|
680
|
+
"""
|
|
681
|
+
Indicates whether this activity has content.
|
|
682
|
+
|
|
683
|
+
:returns: True, if this activity has any content to send; otherwise, false.
|
|
684
|
+
|
|
685
|
+
.. remarks::
|
|
686
|
+
This method is defined on the :class:`Activity` class, but is only intended for use with a message activity,
|
|
687
|
+
where the activity Activity.Type is set to ActivityTypes.Message.
|
|
688
|
+
"""
|
|
689
|
+
if self.text and self.text.strip():
|
|
690
|
+
return True
|
|
691
|
+
|
|
692
|
+
if self.summary and self.summary.strip():
|
|
693
|
+
return True
|
|
694
|
+
|
|
695
|
+
if self.attachments and len(self.attachments) > 0:
|
|
696
|
+
return True
|
|
697
|
+
|
|
698
|
+
if self.channel_data:
|
|
699
|
+
return True
|
|
700
|
+
|
|
701
|
+
return False
|
|
702
|
+
|
|
703
|
+
def is_from_streaming_connection(self) -> bool:
|
|
704
|
+
"""
|
|
705
|
+
Determine if the Activity was sent via an Http/Https connection or Streaming.
|
|
706
|
+
This can be determined by looking at the service_url property:
|
|
707
|
+
(1) All channels that send messages via http/https are not streaming.
|
|
708
|
+
(2) Channels that send messages via streaming have a ServiceUrl that does not begin with http/https.
|
|
709
|
+
|
|
710
|
+
:returns: True if the Activity originated from a streaming connection.
|
|
711
|
+
"""
|
|
712
|
+
if self.service_url:
|
|
713
|
+
return not self.service_url.lower().startswith("http")
|
|
714
|
+
return False
|
|
715
|
+
|
|
716
|
+
def __is_activity(self, activity_type: str) -> bool:
|
|
717
|
+
"""
|
|
718
|
+
Indicates whether this activity is of a specified activity type.
|
|
719
|
+
|
|
720
|
+
:param activity_type: The activity type to check for.
|
|
721
|
+
:return: True if this activity is of the specified activity type; otherwise, False.
|
|
722
|
+
"""
|
|
723
|
+
if self.type is None:
|
|
724
|
+
return False
|
|
725
|
+
|
|
726
|
+
type_attribute = f"ActivityTypes.{str(self.type)}".lower()
|
|
727
|
+
activity_type = str(activity_type).lower()
|
|
728
|
+
|
|
729
|
+
result = type_attribute.startswith(activity_type)
|
|
730
|
+
|
|
731
|
+
if result:
|
|
732
|
+
result = len(type_attribute) == len(activity_type)
|
|
733
|
+
|
|
734
|
+
if not result:
|
|
735
|
+
result = (
|
|
736
|
+
len(type_attribute) > len(activity_type)
|
|
737
|
+
and type_attribute[len(activity_type)] == "/"
|
|
738
|
+
)
|
|
739
|
+
|
|
740
|
+
return result
|
|
741
|
+
|
|
742
|
+
def add_ai_metadata(
|
|
743
|
+
self,
|
|
744
|
+
citations: Optional[list[ClientCitation]] = None,
|
|
745
|
+
usage_info: Optional[SensitivityUsageInfo] = None,
|
|
746
|
+
) -> None:
|
|
747
|
+
"""
|
|
748
|
+
Adds AI entity to an activity to indicate AI-generated content.
|
|
749
|
+
|
|
750
|
+
Args:
|
|
751
|
+
activity: The activity to modify
|
|
752
|
+
citations: Optional list of citations
|
|
753
|
+
usage_info: Optional sensitivity usage information
|
|
754
|
+
"""
|
|
755
|
+
if citations:
|
|
756
|
+
ai_entity = AIEntity(
|
|
757
|
+
type="https://schema.org/Message",
|
|
758
|
+
schema_type="Message",
|
|
759
|
+
context="https://schema.org",
|
|
760
|
+
id="",
|
|
761
|
+
additional_type=["AIGeneratedContent"],
|
|
762
|
+
citation=citations,
|
|
763
|
+
usage_info=usage_info,
|
|
764
|
+
)
|
|
765
|
+
|
|
766
|
+
if self.entities is None:
|
|
767
|
+
self.entities = []
|
|
768
|
+
|
|
769
|
+
self.entities.append(ai_entity)
|
|
770
|
+
|
|
771
|
+
def is_agentic_request(self) -> bool:
|
|
772
|
+
return self.recipient and self.recipient.role in [
|
|
773
|
+
RoleTypes.agentic_identity,
|
|
774
|
+
RoleTypes.agentic_user,
|
|
775
|
+
]
|
|
776
|
+
|
|
777
|
+
def get_agentic_instance_id(self) -> Optional[str]:
|
|
778
|
+
"""Gets the agent instance ID from the context if it's an agentic request."""
|
|
779
|
+
if not self.is_agentic_request() or not self.recipient:
|
|
780
|
+
return None
|
|
781
|
+
return self.recipient.agentic_app_id
|
|
782
|
+
|
|
783
|
+
def get_agentic_user(self) -> Optional[str]:
|
|
784
|
+
"""Gets the agentic user (agenticUserId) from the context if it's an agentic request."""
|
|
785
|
+
if not self.is_agentic_request() or not self.recipient:
|
|
786
|
+
return None
|
|
787
|
+
return self.recipient.agentic_user_id
|