feat: offer retrying a failed encrypted upload without encryption

Many servers reject opaque encrypted files, so report the failure with an action button that re-uploads the file as a plain link, like Amethyst does.
This commit is contained in:
2026-09-15 20:45:32 +07:00
parent c8ee4f63bb
commit ee3547fc86
+58 -6
View File
@@ -714,17 +714,34 @@ impl ChatPanel {
return Ok(());
};
this.update(cx, |this, cx| {
this.set_uploading(true, cx);
this.update_in(cx, |this, window, cx| {
this.upload_file(server, path, encrypted, window, cx);
})?;
// Upload the file, encrypted when it is the whole message
Ok(())
}));
}
/// Upload a file, encrypted when the attachment is the whole message
fn upload_file(
&mut self,
server: Url,
path: PathBuf,
encrypted: bool,
window: &mut Window,
cx: &mut Context<Self>,
) {
self.set_uploading(true, cx);
self.tasks.push(cx.spawn_in(window, async move |this, cx| {
let result = if encrypted {
upload_encrypted(server, path.clone(), cx)
upload_encrypted(server.clone(), path.clone(), cx)
.await
.map(|file| Uploaded::File(file, path))
.map(|file| Uploaded::File(file, path.clone()))
} else {
upload(server, path, cx).await.map(Uploaded::Url)
upload(server.clone(), path.clone(), cx)
.await
.map(Uploaded::Url)
};
this.update_in(cx, |this, window, cx| {
@@ -733,6 +750,9 @@ impl ChatPanel {
match result {
Ok(Uploaded::Url(url)) => this.add_attachment(url, cx),
Ok(Uploaded::File(file, path)) => this.add_pending_file(file, path, cx),
Err(e) if encrypted => {
this.report_encrypted_upload_error(server, path, e, window, cx)
}
Err(e) => {
window.push_notification(
Notification::error(e.to_string()).autohide(false),
@@ -746,6 +766,38 @@ impl ChatPanel {
}));
}
/// Report a failed encrypted upload, offering to retry it without encryption
fn report_encrypted_upload_error(
&mut self,
server: Url,
path: PathBuf,
error: Error,
window: &mut Window,
cx: &mut Context<Self>,
) {
let view = cx.entity().downgrade();
window.push_notification(
Notification::error(error.to_string())
.title("Encrypted upload failed")
.action(move |_this, _window, _cx| {
let view = view.clone();
let server = server.clone();
let path = path.clone();
Button::new("retry-without-encryption")
.label("Upload without encryption")
.on_click(move |_ev, window, cx| {
view.update(cx, |this, cx| {
this.upload_file(server.clone(), path.clone(), false, window, cx);
})
.ok();
})
}),
cx,
);
}
fn set_uploading(&mut self, uploading: bool, cx: &mut Context<Self>) {
self.uploading = uploading;
cx.notify();