Skip to content

compose box: On failed message send, show error dialog #819

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

Merged
merged 3 commits into from
Jul 18, 2024

Conversation

chrisbobbe
Copy link
Collaborator

@chrisbobbe chrisbobbe commented Jul 17, 2024

Fixes: #815

@chrisbobbe chrisbobbe added a-compose Compose box, autocomplete, attaching files/images integration review Added by maintainers when PR may be ready for integration labels Jul 17, 2024
@chrisbobbe chrisbobbe requested a review from gnprice July 17, 2024 20:40
Copy link
Member

@gnprice gnprice left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for taking care of this quickly! Comments below.

Comment on lines 195 to 200
final message = eg.streamMessage(
stream: stream,
topic: 'some topic',
content: 'hello world',
);
await prepareComposeBox(tester, TopicNarrow.ofMessage(message));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's never a real message involved here, right? And in the real-user interaction this is simulating, this isn't a message that would exist at this stage — this is a message that might exist after the user hits send and the server processes that.

So it feels confusing for that test narrative to create a message object here. The test doesn't end up actually using much of it anyway — for example the content here doesn't affect the test. Instead we can use the stream and topic directly:

Suggested change
final message = eg.streamMessage(
stream: stream,
topic: 'some topic',
content: 'hello world',
);
await prepareComposeBox(tester, TopicNarrow.ofMessage(message));
await prepareComposeBox(tester, TopicNarrow(stream.streamId, 'some topic'));

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah indeed!

try {
// TODO(#720) put input(s) and send button into a disabled "working on it"
// state (allowing input text to be selected for copying).
await store.sendMessage(destination: widget.getDestination(), content: content);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This changes more than the error behavior — it also means we wait to clear the content input until the request completes.

Our promptly clearing the input isn't entirely a good thing; that's what #720 is about. But if we take that out without doing the other work called for in #720, I think the effect is that there's a lack of feedback so that it feels like the send button didn't do anything, or is sluggish.

Trying this, I notice that even on my fast home network connection. Then to demonstrate how it behaves when the request is especially slow, try this patch:

--- lib/api/core.dart
+++ lib/api/core.dart
@@ -188,6 +188,7 @@ class ApiConnection {
     if (params != null) {
       request.bodyFields = encodeParameters(params)!;
     }
+    await Future<void>.delayed(const Duration(seconds: 2));
     return send(routeName, fromJson, request, overrideUserAgent: overrideUserAgent);
   }
 

The way to fix that looks something like:

final sendFuture = store.sendMessage(…);
widget.contentController.clear();

try {
  await sendFuture;
} on

Or I guess more straightforwardly, we can just call clear before sendMessage.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Makes sense.

@chrisbobbe chrisbobbe force-pushed the pr-message-send-failure-dialog branch from c56963e to bdb0f1c Compare July 17, 2024 21:27
@chrisbobbe
Copy link
Collaborator Author

Thanks for the review! Revision pushed.

Comment on lines 743 to 746
// TODO(#720) await send request, putting input(s) and send button into a
// disabled "working on it" state (allowing input text to be selected
// for copying).
await store.sendMessage(destination: widget.getDestination(), content: content);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: first clause of the TODO sounds like a description of what the code is already doing


group('message-send request response', () {
Future<void> setupAndTapSend(WidgetTester tester, {
required void Function(int) prepareResponse,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: can give a hint what the callback parameter means:

Suggested change
required void Function(int) prepareResponse,
required void Function(int messageId) prepareResponse,

(wasn't so necessary when the type was Message)

Copy link
Member

@gnprice gnprice left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the revision! Two nits above, and otherwise LGTM.

@alya
Copy link
Collaborator

alya commented Jul 17, 2024

Maybe we can drop "The server said:" part? It doesn't seem necessary to me from an end user perspective.

@gnprice
Copy link
Member

gnprice commented Jul 17, 2024

In general this error dialog is handling an error that the server gave us but we didn't anticipate. (Anticipating this particular error is #791, which is behind a couple of larger prerequisite issues.)

So that's meant to be a situation that's rare; and because we didn't anticipate the error, it's also possible that the text is somewhat obscure or out of context. That's why I think it's potentially helpful to disambiguate that this is text from the server and not some other error message from within the app.

We use the same pattern in handling some other errors too, so it'd be easy to change them all together.

@alya
Copy link
Collaborator

alya commented Jul 18, 2024

Ok. Might be worth discussing in #mobile, but definitely not a blocker for merging this PR, given that context.

@chrisbobbe chrisbobbe force-pushed the pr-message-send-failure-dialog branch from bdb0f1c to 3256d1a Compare July 18, 2024 23:06
@chrisbobbe
Copy link
Collaborator Author

Thanks for the review! Revision pushed.

@gnprice gnprice merged commit 3256d1a into zulip:main Jul 18, 2024
1 check passed
@gnprice
Copy link
Member

gnprice commented Jul 18, 2024

Thanks! Looks good — merging.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
a-compose Compose box, autocomplete, attaching files/images integration review Added by maintainers when PR may be ready for integration
Projects
None yet
Development

Successfully merging this pull request may close these issues.

On failed message send, show error dialog
3 participants