Open Bug 1788159 Opened 2 years ago Updated 6 months ago

Simplify nsMessenger attachment methods

Categories

(MailNews Core :: Backend, task)

Tracking

(Not tracked)

People

(Reporter: benc, Unassigned)

References

Details

The nsIMessenger attachment functions seem a little convoluted.

Here are my proposals on what should change:

saveAllAttachments()

  • Don't prompt for filenames. Make the caller pass in destination path(s) up front
  • Single messageUri rather than array? (all attachments must be from same message, right?)
  • Rename to saveAttachments()
  • Make sure it works with multiple attachments
  • Add unit tests (there's a mochitest, but no xpcshell test)

detachAllAttachments()

  • Rename to detachAttachments().
  • Add a listener to trigger when complete.
  • Ditch saveFirst option (make the caller do it - easy if there's listener support!)
  • Single messageUri rather than array? (all attachments must be from same message, right?)
  • No UI prompting (not sure if it does or not right now).
  • Caller to pass in list of file urls for previously-detached attachments (to fill out X-Mozilla-External-Attachment-URL headers in the deleted attachements).
  • Make sure it works with multiple attachments
  • Add unit tests (there's a mochitest, but no xpcshell test)

detachAttachmentsWOPrompt()

  • Ditch entirely, use detachAttachments() instead.

detachAttachment()

  • Ditch entirely, use detachAttachments() instead.

saveAttachment()

  • Ditch entirely, use saveAttachments() instead.
See Also: → 1786237
See Also: → 1789565

Implementation notes:

So many moving parts, so much undefined ownership, so much scope for leaks and bad error handling!

Current system involves:

  • nsSaveAllAttachmentsState - a data-only (mostly) class which holds a list of items to save, and a flag to say if they should also be detached afterwards.
  • nsMessenger::SaveAttachment() (the internal one, not the NS_IMETHODIMP one) - handles a single item, by creating a nsSaveMsgListener. But takes an nsSaveAllAttachmentsState object which holds all the items to be processed.
  • nsSaveMsgListener - handles just a single item. But has an nsSaveAllAttachments, which it uses to kick off the next save (by calling nsMessenger::SaveAttachment() again!), and/or to kick off a Detachment phase.

nsSaveMsgListener handles destroying the nsSaveAllAttachmentsState once all the items are saved... but it's the ownership is pretty odd and there's a lot of scope for leaks and oddness and non-invoked listeners when errors occur!

Suggestion:

  • merge nsSaveMsgListener and nsSaveAllAttachmentsState and nsMessenger::SaveAttachment() into one class.
  • use modern C++ lambdas to replace the current callback soup (nsSaveMsgListener currently derives from nsIUrlListener, nsIMsgCopyServiceListener, nsIStreamListener, nsICancelable and it's really not clear which callbacks are used by which calls! The inheritance is all public, and exposed to the caller, where it's really just implementation detail).
  • make it really bulletproof! Clean ownership of everything to avoid leaks, and clear start/stop/error handling to ensure callers don't hang upon listener notifications which never come...
  • look at nsAttachmentState and see where it fits in to all this.
Blocks: 1864344
No longer blocks: 1864344

As per Bug 1135434, the detach-attachment-from-a-message on IMAP could also use some attention.

See Also: → 1135434
See Also: → 1864344
You need to log in before you can comment on or make changes to this bug.