store.FetchFull: Change callback type to expose entire message

This is a prerequisite for allowing the FetchFull message to return both
the message content and the message headers.
This commit is contained in:
Ben Fiedler 2020-04-24 22:31:39 +02:00 committed by Drew DeVault
parent b650bb30a2
commit 05fa79eb8e
5 changed files with 17 additions and 11 deletions

View file

@ -12,6 +12,8 @@ import (
"git.sr.ht/~sircmpwn/aerc/models" "git.sr.ht/~sircmpwn/aerc/models"
"git.sr.ht/~sircmpwn/aerc/widgets" "git.sr.ht/~sircmpwn/aerc/widgets"
"git.sr.ht/~sircmpwn/aerc/worker/types"
"git.sr.ht/~sircmpwn/getopt" "git.sr.ht/~sircmpwn/getopt"
) )
@ -109,7 +111,7 @@ func (forward) Execute(aerc *widgets.Aerc, args []string) error {
} }
tmpFileName := path.Join(tmpDir, tmpFileName := path.Join(tmpDir,
strings.ReplaceAll(fmt.Sprintf("%s.eml", msg.Envelope.Subject), "/", "-")) strings.ReplaceAll(fmt.Sprintf("%s.eml", msg.Envelope.Subject), "/", "-"))
store.FetchFull([]uint32{msg.Uid}, func(reader io.Reader) { store.FetchFull([]uint32{msg.Uid}, func(fm *types.FullMessage) {
tmpFile, err := os.Create(tmpFileName) tmpFile, err := os.Create(tmpFileName)
if err != nil { if err != nil {
println(err) println(err)
@ -119,7 +121,7 @@ func (forward) Execute(aerc *widgets.Aerc, args []string) error {
} }
defer tmpFile.Close() defer tmpFile.Close()
io.Copy(tmpFile, reader) io.Copy(tmpFile, fm.Content.Reader)
composer, err := addTab() composer, err := addTab()
if err != nil { if err != nil {
return return

View file

@ -9,6 +9,7 @@ import (
"git.sr.ht/~sircmpwn/aerc/commands" "git.sr.ht/~sircmpwn/aerc/commands"
"git.sr.ht/~sircmpwn/aerc/widgets" "git.sr.ht/~sircmpwn/aerc/widgets"
"git.sr.ht/~sircmpwn/aerc/worker/types"
"git.sr.ht/~sircmpwn/getopt" "git.sr.ht/~sircmpwn/getopt"
"github.com/gdamore/tcell" "github.com/gdamore/tcell"
@ -115,11 +116,11 @@ func (Pipe) Execute(aerc *widgets.Aerc, args []string) error {
if err != nil { if err != nil {
return err return err
} }
store.FetchFull([]uint32{msg.Uid}, func(reader io.Reader) { store.FetchFull([]uint32{msg.Uid}, func(fm *types.FullMessage) {
if background { if background {
doExec(reader) doExec(fm.Content.Reader)
} else { } else {
doTerm(reader, fmt.Sprintf( doTerm(fm.Content.Reader, fmt.Sprintf(
"%s <%s", cmd[0], msg.Envelope.Subject)) "%s <%s", cmd[0], msg.Envelope.Subject))
} }
}) })

View file

@ -12,6 +12,7 @@ import (
"git.sr.ht/~sircmpwn/aerc/models" "git.sr.ht/~sircmpwn/aerc/models"
"git.sr.ht/~sircmpwn/aerc/worker/lib" "git.sr.ht/~sircmpwn/aerc/worker/lib"
"git.sr.ht/~sircmpwn/aerc/worker/types"
) )
// This is an abstraction for viewing a message with semi-transparent PGP // This is an abstraction for viewing a message with semi-transparent PGP
@ -65,7 +66,8 @@ func NewMessageStoreView(messageInfo *models.MessageInfo,
nil, nil, messageInfo.BodyStructure} nil, nil, messageInfo.BodyStructure}
if usePGP(messageInfo.BodyStructure) { if usePGP(messageInfo.BodyStructure) {
store.FetchFull([]uint32{messageInfo.Uid}, func(reader io.Reader) { store.FetchFull([]uint32{messageInfo.Uid}, func(fm *types.FullMessage) {
reader := fm.Content.Reader
pgpReader, err := pgpmail.Read(reader, Keyring, decryptKeys, nil) pgpReader, err := pgpmail.Read(reader, Keyring, decryptKeys, nil)
if err != nil { if err != nil {
panic(err) panic(err)

View file

@ -20,7 +20,7 @@ type MessageStore struct {
uids []uint32 uids []uint32
selected int selected int
bodyCallbacks map[uint32][]func(io.Reader) bodyCallbacks map[uint32][]func(*types.FullMessage)
headerCallbacks map[uint32][]func(*types.MessageInfo) headerCallbacks map[uint32][]func(*types.MessageInfo)
//marking //marking
@ -64,7 +64,7 @@ func NewMessageStore(worker *types.Worker,
selected: 0, selected: 0,
marked: make(map[uint32]struct{}), marked: make(map[uint32]struct{}),
bodyCallbacks: make(map[uint32][]func(io.Reader)), bodyCallbacks: make(map[uint32][]func(*types.FullMessage)),
headerCallbacks: make(map[uint32][]func(*types.MessageInfo)), headerCallbacks: make(map[uint32][]func(*types.MessageInfo)),
defaultSortCriteria: defaultSortCriteria, defaultSortCriteria: defaultSortCriteria,
@ -105,7 +105,7 @@ func (store *MessageStore) FetchHeaders(uids []uint32,
} }
} }
func (store *MessageStore) FetchFull(uids []uint32, cb func(io.Reader)) { func (store *MessageStore) FetchFull(uids []uint32, cb func(*types.FullMessage)) {
// TODO: this could be optimized by pre-allocating toFetch and trimming it // TODO: this could be optimized by pre-allocating toFetch and trimming it
// at the end. In practice we expect to get most messages back in one frame. // at the end. In practice we expect to get most messages back in one frame.
var toFetch []uint32 var toFetch []uint32
@ -117,7 +117,7 @@ func (store *MessageStore) FetchFull(uids []uint32, cb func(io.Reader)) {
if list, ok := store.bodyCallbacks[uid]; ok { if list, ok := store.bodyCallbacks[uid]; ok {
store.bodyCallbacks[uid] = append(list, cb) store.bodyCallbacks[uid] = append(list, cb)
} else { } else {
store.bodyCallbacks[uid] = []func(io.Reader){cb} store.bodyCallbacks[uid] = []func(*types.FullMessage){cb}
} }
} }
} }
@ -233,7 +233,7 @@ func (store *MessageStore) Update(msg types.WorkerMessage) {
delete(store.pendingBodies, msg.Content.Uid) delete(store.pendingBodies, msg.Content.Uid)
if cbs, ok := store.bodyCallbacks[msg.Content.Uid]; ok { if cbs, ok := store.bodyCallbacks[msg.Content.Uid]; ok {
for _, cb := range cbs { for _, cb := range cbs {
cb(msg.Content.Reader) cb(msg)
} }
delete(store.bodyCallbacks, msg.Content.Uid) delete(store.bodyCallbacks, msg.Content.Uid)
} }

View file

@ -166,6 +166,7 @@ type MessageInfo struct {
type FullMessage struct { type FullMessage struct {
Message Message
Info *models.MessageInfo
Content *models.FullMessage Content *models.FullMessage
} }