-
Notifications
You must be signed in to change notification settings - Fork 2.9k
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
Communication chat preview4 #16905
Communication chat preview4 #16905
Conversation
* Add generated chat code from new swagger * Change to use new generated code * Address PR Feedback * Remove CommunicationUserIdentifierModel in identity,phone number package
* Replace identifier with rawId * Change serilizer * Replace indentifier with rawId in test code * Sync models across modules * fix typo in serizliser * Rearrange imports * Replace rawId with raw_id * remove trailing newline Co-authored-by: turalf <tufarhad@microsoft.com>
- CommunicationUserIdentifier models added - create_chat_thread - returns CreateChatThreadResult instead of ChatThreadClient - add_participant - docstring update AddChatParticipantsResult instead of None - add_participants - docstring update AddChatParticipantsResult instead of None
PR includes changes from https://github.com/Azure/azure-sdk-for-python/tree/feature/preview4 as well |
@@ -500,14 +501,14 @@ async def add_participants( | |||
self, | |||
thread_participants: List[ChatThreadParticipant], | |||
**kwargs | |||
) -> None: | |||
) -> AddChatParticipantsResult: |
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.
We should unpackage this result type. It's currently pretty hard to use...
If you could write a sample demonstrating what a customer has to do to:
- Add 5 participants
- Determine which 2 our of those 5 failed.
- Re-attempt to add those 2 failures.
From their we can figure out the best response value 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.
@annatisch something like this?
def _util_create_thread_participant(user, **kwargs) -> ChatThreadParticipant:
"""
Create util or call the constructor of ChatThreadParticipant - same thing
"""
return ChatThreadParticipant(
user=user_id,
display_name = kwargs.get('display_name', None),
share_history_time = kwargs.get('share_history_time', None)
)
def decide_if_needs_to_retried(invalid_participant) -> bool:
"""
some logic to determine if this is needed to be retried or not
"""
return True
if __name__=='__main__':
# intialize identity client
identity_client = CommunicationIdentityClient.from_connection_string(connection_string)
# initialize and retrieve chat_thread_client
refresh_options = CommunicationTokenRefreshOptions(token)
chat_client = ChatClient(endpoint, CommunicationTokenCredential(refresh_options))
topic = "some topic"
participants = [ChatThreadParticipant(
user=user, # whoever is creating the chat_thread
display_name='name',
share_history_time=datetime.utcnow()
)]
create_chat_thread_result = chat_client.create_chat_thread(topic, participants)
chat_thread_client = chat_client.get_chat_thread_client(create_chat_thread_result.chat_thread.id)
# initialize 3+2 participants
users_for_sucesss = [identity_client.create_user() for i in range(3)] # create 3 users for success - type: List[CommunicationUserIdentifier]
users_for_failures = [CommunicationUserIdentifier("some random id 1"), CommunicationUserIdentifier("some random id 2")] # create 2 users for failures - type: List[CommunicationUserIdentifier]
# create ChatThreadParticipant objects
participants_success = [_util_create_thread_participant(user) for user in users_for_sucesss]
participants_failures = [_util_create_thread_participant(user) for user in users_for_failures]
# add participants to chat thread
thread_participants = [participants_success + participants_failures]
add_chat_participants_result = chat_thread_client.add_participants(thread_participants)
# verify if all participants have been added or not
participants_to_retry = [] # in case of failure store participants to be retried - type: List[CommunicationUserIdentifier]
if hasattr(add_chat_participants_result, 'errors') and \
add_chat_participants_result.errors is not None:
print("Error encountered in adding ", len(thread_participants), " participants")
participant_failed_to_add = add_chat_participants_result.errors.invalid_participants
for failed_participant in participant_failed_to_add:
# failed_participant.target contains the user_id - type: str
# For example, in this scenario the values would be either 'some random id 1' or 'some random id 2'
print("Failed to add participant", failed_participant.target)
if decide_if_needs_to_retried(failed_participant):
participants_to_retry.append(CommunicationUserIdentifier(failed_participant.target))
# if any user has been failed to be added, then retry
if len(participants_to_retry) != 0:
thread_participants = [_util_create_thread_participant(retry_user) for retry_user in participants_to_retry]
add_chat_participants_result_retry = chat_thread_client.add_participants(thread_participants)
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.
Wow that's lots of code... and a couple of red flags. If a customer ever has to call hasattr
on the response of call, then we did something wrong :)
If we change the return type to: List[Tuple[ChatThreadParticipant, Optional[AddParticipantError]]
Then we could replace all this:
add_chat_participants_result = chat_thread_client.add_participants(thread_participants)
# verify if all participants have been added or not
participants_to_retry = [] # in case of failure store participants to be retried - type: List[CommunicationUserIdentifier]
if hasattr(add_chat_participants_result, 'errors') and \
add_chat_participants_result.errors is not None:
print("Error encountered in adding ", len(thread_participants), " participants")
participant_failed_to_add = add_chat_participants_result.errors.invalid_participants
for failed_participant in participant_failed_to_add:
# failed_participant.target contains the user_id - type: str
# For example, in this scenario the values would be either 'some random id 1' or 'some random id 2'
print("Failed to add participant", failed_participant.target)
if decide_if_needs_to_retried(failed_participant):
participants_to_retry.append(CommunicationUserIdentifier(failed_participant.target))
# if any user has been failed to be added, then retry
if len(participants_to_retry) != 0:
thread_participants = [_util_create_thread_participant(retry_user) for retry_user in participants_to_retry]
add_chat_participants_result_retry = chat_thread_client.add_participants(thread_participants)
With just a couple of lines:
result = chat_thread_client.add_participants(thread_participants)
failed = [p for p, error in result if decide_if_needs_to_retried(error)]
retry = chat_thread_client.add_participants(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.
@annatisch The following changes have been made
- add_participant - AddChatParticipantsResult -> tuple(ChatThreadParticipant, CommunicationError)
- add_participants - AddChatParticipantsResult -> list(tuple(ChatThreadParticipant, CommunicationError))
- CreateChatThreadResult -> attributes changed to
- chat_thread -> ChatThread (no change)
- Errors -> CreateChatThreadErrors -> list(tuple(ChatThreadParticipant, CommunicationError))
- add_participant - AddChatParticipantsResult -> tuple(ChatThreadParticipant, CommunicationError) - add_participants - AddChatParticipantsResult -> list(tuple(ChatThreadParticipant, CommunicationError)) - unit tests modified as per signature change - CommunicationErrorResponseConverter added to cosolidate list(ChatThreadParticipant) and list(CommunicationError) into list(tuple(ChatThreadParticipant, CommunicationError)) - e2e tests modified as per signature change
…ls with ease - CreateChatThreadResult -> attributes changed to - chat_thread -> ChatThread (no change) - Errors -> CreateChatThreadErrors -> list(tuple(ChatThreadParticipant, CommunicationError)) - create_chat_thread -> `thread_participants` and `repeatability_request_id` changed to keyword arguments - Modify unit tests to capture method signature modifications - Modify e2e tests to capture method signature modifications
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.
Looking good - I think we're nearly there :)
@@ -478,14 +483,16 @@ def add_participant( | |||
thread_participant, # type: ChatThreadParticipant | |||
**kwargs # type: Any | |||
): | |||
# type: (...) -> None | |||
# type: (...) -> tuple(ChatThreadParticipant, CommunicationError) |
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.
In the case of the single add_participant
, we shouldn't return the error object - we should just raise an error.
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.
@annatisch we mentioned this one on the .NET review:
https://apiview.dev/Assemblies/Review/a60a130cc1e24d65a74c20e42887b61f#74d339479f13486ebababaee478f8990
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.
@annatisch add_participant
raises error - change implemented
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.
@annatisch are we ok with having this diverge in python ? I am ok if you are.
When we run this in that meeting, the answer was to leave it as is in case in the future any additional data is required back from that call. I don't see that coming but that was the decision.
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.
@juancamilor - raising errors rather than returning them is Pythonic behaviour that I would expect to differ from .Net.
We can still return the ChatThreadParticipant
object - when you say additional data, you mean other information outside of these two fields?
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.
yes, something like extra headers is what Ted G mentioned, but I don't have any requirements yet to back it up.
tg-msft1
There aren't today, but maybe it'll come back with extra headers in the future?
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.
@annatisch after today's review we will address all the changes on the next iteration (including the removal of this operation).
- Update README.md with modified signature - Update samples with new method signatures - Add test to detect invalid instantiation of AccessToken - Minor documentation updates - Modify unit tests to capture method signature modifications - Modify e2e tests to capture method signature modifications
3683f00
into
Azure:feature/communication-chat-preview4-comm-models
* [Communication] Generate identifier Models from new swagger (#16735) * Add generated chat code from new swagger * Address PR Feedback * Remove CommunicationUserIdentifierModel in identity,phone number package * Check schema of the object to determine the type [preview4] (#16838) * Replace identifier with rawId * Change serilizer * Replace indentifier with rawId in test code * Sync models across modules * fix typo in serizliser * Rearrange imports * Replace rawId with raw_id * remove trailing newline Co-authored-by: turalf <tufarhad@microsoft.com> * preview4 changes made + unit tests fixed * Chat - preview4 changes - CommunicationUserIdentifier models added - create_chat_thread - returns CreateChatThreadResult instead of ChatThreadClient - add_participant - docstring update AddChatParticipantsResult instead of None - add_participants - docstring update AddChatParticipantsResult instead of None * pylint-changes * pylint changes * Method signature changed for add_pariticipant and add_participants - add_participant - AddChatParticipantsResult -> tuple(ChatThreadParticipant, CommunicationError) - add_participants - AddChatParticipantsResult -> list(tuple(ChatThreadParticipant, CommunicationError)) - unit tests modified as per signature change - CommunicationErrorResponseConverter added to cosolidate list(ChatThreadParticipant) and list(CommunicationError) into list(tuple(ChatThreadParticipant, CommunicationError)) - e2e tests modified as per signature change * CreateChatThreadResult modified to handle partial errors in batch calls with ease - CreateChatThreadResult -> attributes changed to - chat_thread -> ChatThread (no change) - Errors -> CreateChatThreadErrors -> list(tuple(ChatThreadParticipant, CommunicationError)) - create_chat_thread -> `thread_participants` and `repeatability_request_id` changed to keyword arguments - Modify unit tests to capture method signature modifications - Modify e2e tests to capture method signature modifications * pylint-changes * pylint fixes * README.md update + pylint fixes * test recordings added * add_participant -> raises error - Update README.md with modified signature - Update samples with new method signatures - Add test to detect invalid instantiation of AccessToken - Minor documentation updates - Modify unit tests to capture method signature modifications - Modify e2e tests to capture method signature modifications * pylint fixes * cls removed from docstring + update_topic async refactored * cls removed from docstring Co-authored-by: Sam Cheung <sacheu@microsoft.com> Co-authored-by: turalf <tural.ferhadov@gmail.com> Co-authored-by: turalf <tufarhad@microsoft.com> Co-authored-by: Sam Cheung <sacheu@microsoft.com> Co-authored-by: turalf <tural.ferhadov@gmail.com> Co-authored-by: turalf <tufarhad@microsoft.com>
…into http_request_json * 'master' of https://github.com/Azure/azure-sdk-for-python: (147 commits) [text analytics] add perf tests (Azure#17060) Add cloud event to core (Azure#16800) [Perf] Small fixes to storage-blob (Azure#17055) [EG] Regenerate Code (Azure#17053) Scrub batch shared keys (Azure#17030) [Tables] Add SAS to tables (Azure#16717) T2 containerservice 2021 03 03 (Azure#17050) Addressing issues with CredScan (Azure#16944) Communication chat preview4 (Azure#16905) (Azure#17037) remove first query section (Azure#17033) [formrecognizer] temp disable sample tests until service bug fixed (Azure#17036) [device update] allow device update pylint failures (Azure#17034) fix build (Azure#17029) update artifact names for ALL packages to align with the actual package name Create azure-iot-nspkg (Azure#17026) [Communication]: SMS 1:N Messages, Custom Tags, and Idempotence (Azure#16836) Fixing credentials to use AAD (Azure#16885) T2 deviceupdate 2021 03 02 (Azure#17016) T2 cosmosdb 2021 02 23 (Azure#16875) T2 datadog 2021 03 02 (Azure#17004) ...
thread_participants
andrepeatability_request_id
changed to keyword arguments