One way to approach it could be to leave the current transaction object intact but add a method to say/query "do the recipients individually" and then have a method to access the individual ones. That way we can move plugins that need the extra information to use it and the ones that don't care to, uh, not.
literally doing every recipient individually is suboptimal IMO. In our case we have a very robust system of inheritance that some clients make use of and some do not -- so when you send a message to 20 users at 3 different hosted domains, you might wind up with 20 different sets of expected behavior, or 10, or 3, or 1. Dealing with the structure as it is now is certainly not easy or straightforward, but the possibility of being able to deal with split out lists of recips rather than all-at-once or one-at-a-time is exciting to me, it could really help resources in a lot of situations while retaining a lot of potential granularity. Of course time and testing will tell whether this really makes a big difference.
Of course there are a bunch of edge cases -- what do you do when you can/have queue(d) one message but the second one failed?
to deal with these situations we are implementing a sort of "downgrading" mechanism which is once again configurable... no great solution exists but at least users can pick their poison. For instance to deal with the question of what to return to the client if half the recips wanted to reject a message and respond with 5xx and half of them want to recieve it and respond with 250, we downgrade the recipients that would have rejected to whatever they (or their parents or the defaults) chose - delete, tag, quarantine, bounce, etc. -- and then return 250 to the client and queue the mail to the ones that wanted it. Of course we are putting off 'live' message queueing for now and just injecting into postfix to queue, so we don't yet have to deal with the issue of all the recipients wanted the message queued and half of them couldn't queue it. But such a system would probably map well to that problem.
Anyway - it's great that you are starting on this; some real world use cases will make it easier to guide the API.
I'll let you know what we come up with, although whatever it is might be too narrow to be very useful for a product that has to remain workable in other situations than ours :)
-Jared Johnson Software Developer and Support Engineer Network Management Group, Inc. 620-664-6000 x118 -- Inbound and outbound email scanned for spam and viruses by the DoubleCheck Email Manager: http://www.doublecheckemail.com/