I have implemented a plug-in for SquirrelMail that uses Option #2. When the user clicks "Train as Junk", the message is moved to a different IMAP folder (usually called "Train as Junk"). Normally, the user is not subscribed to this folder, so isn't aware that it exists. "Train as Not Junk" transfers messages to the "Train as Not Junk" folder. Once every two minutes, a cron job checks the folder, trains and redelivers messages found there. I think something similar would work nicely in Roundcube, but this kind of addition would be better done as a plug-in -- once an extensibility model is defined, of course.
If you're curious about how I did this for SquirrelMail, have a look here:
http://www.convoglio.com/crm114/-Steve