On 02/15/12 16:34, Mildred Ki'Lya wrote:
> To use Trojita, I would need draft support (messages should be saved as
> drafts until sent) to prevents from loosing a message if the SMTP
> transaction fails. I was thinking of the following way of implementing it:

Hi Mildred, thanks for your interest. Code which is responsible for
message composing and sending is in a rather sad state, unfortunately.
I'm currently focusing on the IMAP part of Trojita, so if you'd like to
improve upon these areas, please go ahead, that'd be very welcome.

> - if a message is a draft, the message view allows to edit it
> - if the message is not a draft, an action would allow to duplicate the
> message and edit the duplicated one as a draft
> - everything should be editable in a draft
> - creating a new message (or replying to an existing one) would create a
> draft message on the server, and it would be edited from there

This looks reasonable.

> - draft could be sent through SMTP or other means (I think some IMAP
> servers support sending messages in a specific mailbox). This would
> remove the draft flag from the message

I'm not aware of any existing way of asking the IMAP server to just send
an already composed message; there's SMTP's BURL extension and some
effort to address this in Bron's IMAP5 design, but nothing just in IMAP
and its current extensions, unfortunately.

> I am also very interested in looking at message flags/keywords, so I
> already made a little modification, consisting in showing the flags of a
> message in the message view. It will probably need to get its UI
> improved. I pushed it on my repository:
> https://gitorious.org/~mildred/trojita/mildreds-trojita

That's a good start, and I've merged that into my tree with a few
modifications (see [1]) -- thanks for your patch.

Right now, these flags don't get updated when the flags change on the
IMAP side, but I think this is fine for now.

> Next, I'd also like to be able to add/remove a flag from a message.
> Apparently the underlying model doesn't allow write operations, so I'd
> need to use a Task object. I believe this touches the underlying IMAP
> protocol. I think I saw somewhere that modifying this layer was
> restricted ... I'd like to know how much, and how I can improve Trojita
> and be sure my modifications can be accepted.
> 
> Also, I was wondering, why not make the message model
> (Imap::Mailbox::TreeItem / Imap::Mailbox::Model) accept write operations
> (the setData method). Would it be acceptable to write a setData method
> in the model that would create Task objects ?

I'd prefer not going through the setData() method, but instead adding
something like this to the Imap::Mailbox::Model:

typedef enum FlagOperation { FLAGS_ADD, FLAGS_REMOVE, FLAGS_SET };

void updateMessageFlags(const QModelIndexList &messages,
  const FlagOperation operation, const QStringList &flags);

The markMessagesDeleted & markMessagesRead shall be ported to use this
method, then.

Would that work for you? I'll happily accept such a patch.

The reason for my preference for a dedicated method instead of reusing
the generic setData() is that in IMAP, essentially everything about a
given message is immutable. You cannot really edit a message, you can
only append a new one at the end of a mailbox and delete the old one.
Once a message has arrived, its data cannot change anymore.

The only exception which has a practical meaning outside of the IMAP
model are the message flags, so if there was a setData() function, it
would have to return "sorry, can't do that" in most cases anyway. In
addition, IMAP allows for an efficient partial updates of flags ("add
the \Deleted to the list of flags") instead of a potentially race-prone
read-modify-write cycle, and that's simply not possible with setData().

Now, given that a message cannot change, this is going to have a few
implications on how the "Edit as Draft" is going to behave. If I was
designing that feature, I'd probably do the editing on the client side
(this would require a revamped composer capable of building a MIME
message from its parts), saving to the server every now and then (be
careful there, that might be a bandwidth-heavy operation -- its impact
could be reduced a bit by the CATENATE extension, but that's would
require even more work).

Towards you core goal of working with flags -- I guess what you'd like
to have is something like a tree view of all possible flags to
replace/augment the mailbox listing on Trojita's left hand side. That's
not going to be too hard -- Trojita will always sync the flags when it
opens a mailbox, and changes in the flag data are properly communicated
through dataChanged() (at least I hope so, and if they aren't, that'd be
a bug).  You could easily attach a QSortFilterProxyModel on top of the
relevant PrettyMsgListModel.

In real world, this is going to be slightly harder due to the way how
QSortFilterProxyModel interacts with tree data (as produced by the
ThreadingMsgListModel). Suppose the following thread of messages and
their flags:

* root item (foo, bar)
  +- Re: root item (bar)
     +- Re: Re: root item (foo)

If you're currently showing a list of messages with the "foo" keyword, a
QSFPM on top the ThreadingMsgListModel would show just the root item
(due to the way how Qt-based filtering of tree models work). A proper
fix would hence have to go to the ThreadingMsgListModel, and that's what
I will have to do in near future anyway.

So, to conclude -- I'm happy to assist you with these changes, and if
you have any questions, just ask, either on this ML, or on IRC (#trojita
on freenode.net; I'm in UTC+1 currently).

Have fun,
Jan

[1]
http://gitorious.org/trojita/trojita/commit/7613711e73fc803a7495e80cc49f21d6790fcac5

-- 
Trojita, a fast e-mail client -- http://trojita.flaska.net/

Attachment: signature.asc
Description: OpenPGP digital signature

Reply via email to