forked from Silverfish/proton-bridge
GODT-1986: Handle case where an address has no decryption entities
It's possible (but very rare, I don't think proton still allows it) for an address to have no keys. If we try to load the address keyring for such an address, this change logs a warning that no decryption entities were found in the unlocked keyring. It bumps liteapi to a version that does not return an error when no keys could be unlocked.
This commit is contained in:
@ -33,6 +33,8 @@ type API interface {
|
||||
|
||||
CreateAddress(userID, address string, password []byte) (string, error)
|
||||
RemoveAddress(userID, addrID string) error
|
||||
GetAddressKeyIDs(userID, addrID string) ([]string, error)
|
||||
RemoveAddressKey(userID, addrID, keyID string) error
|
||||
|
||||
Close()
|
||||
}
|
||||
|
||||
@ -97,6 +97,7 @@ func TestFeatures(testingT *testing.T) {
|
||||
ctx.Step(`^the account "([^"]*)" has the following custom mailboxes:$`, s.theAccountHasTheFollowingCustomMailboxes)
|
||||
ctx.Step(`^the address "([^"]*)" of account "([^"]*)" has the following messages in "([^"]*)":$`, s.theAddressOfAccountHasTheFollowingMessagesInMailbox)
|
||||
ctx.Step(`^the address "([^"]*)" of account "([^"]*)" has (\d+) messages in "([^"]*)"$`, s.theAddressOfAccountHasMessagesInMailbox)
|
||||
ctx.Step(`^the address "([^"]*)" of account "([^"]*)" has no keys$`, s.theAddressOfAccountHasNoKeys)
|
||||
|
||||
// ==== BRIDGE ====
|
||||
ctx.Step(`^bridge starts$`, s.bridgeStarts)
|
||||
|
||||
@ -58,4 +58,22 @@ Feature: Bridge can fully sync an account
|
||||
| Folders/one | 2 | 1 |
|
||||
| Folders/two | 2 | 1 |
|
||||
| Labels | 0 | 0 |
|
||||
| Labels/three | 0 | 0 |
|
||||
| Labels/three | 0 | 0 |
|
||||
|
||||
Scenario: If an address has no keys, the account is still synced
|
||||
Given the account "user@pm.me" has additional address "alias@pm.me"
|
||||
And the account "user@pm.me" has the following custom mailboxes:
|
||||
| name | type |
|
||||
| encrypted | folder |
|
||||
And the address "alias@pm.me" of account "user@pm.me" has the following messages in "encrypted":
|
||||
| from | to | subject |
|
||||
| a@pm.me | a@pm.me | no key |
|
||||
| b@pm.me | b@pm.me | no key |
|
||||
And the address "alias@pm.me" of account "user@pm.me" has no keys
|
||||
When the user logs in with username "user@pm.me" and password "password"
|
||||
And user "user@pm.me" finishes syncing
|
||||
When user "user@pm.me" connects and authenticates IMAP client "1"
|
||||
Then IMAP client "1" eventually sees the following messages in "Folders/encrypted":
|
||||
| from | to | subject | mime-type |
|
||||
| a@pm.me | a@pm.me | no key | multipart/encrypted |
|
||||
| b@pm.me | b@pm.me | no key | multipart/encrypted |
|
||||
@ -18,7 +18,9 @@
|
||||
package tests
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"io"
|
||||
"reflect"
|
||||
"strconv"
|
||||
"strings"
|
||||
@ -35,6 +37,7 @@ import (
|
||||
type Message struct {
|
||||
Subject string `bdd:"subject"`
|
||||
Body string `bdd:"body"`
|
||||
MIMEType string `bdd:"mime-type"`
|
||||
Attachments string `bdd:"attachments"`
|
||||
MessageID string `bdd:"message-id"`
|
||||
|
||||
@ -80,7 +83,17 @@ func newMessageFromIMAP(msg *imap.Message) Message {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
m, err := message.Parse(msg.GetBody(section))
|
||||
literal, err := io.ReadAll(msg.GetBody(section))
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
mimeType, _, err := rfc822.Parse(literal).ContentType()
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
m, err := message.Parse(bytes.NewReader(literal))
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
@ -96,6 +109,7 @@ func newMessageFromIMAP(msg *imap.Message) Message {
|
||||
message := Message{
|
||||
Subject: msg.Envelope.Subject,
|
||||
Body: body,
|
||||
MIMEType: string(mimeType),
|
||||
Attachments: strings.Join(xslices.Map(m.Attachments, func(att message.Attachment) string { return att.Name }), ", "),
|
||||
MessageID: msg.Envelope.MessageId,
|
||||
Unread: !slices.Contains(msg.Flags, imap.SeenFlag),
|
||||
@ -169,7 +183,7 @@ func matchMailboxes(have, want []Mailbox) error {
|
||||
func eventually(condition func() error) error {
|
||||
ch := make(chan error, 1)
|
||||
|
||||
timer := time.NewTimer(10 * time.Second)
|
||||
timer := time.NewTimer(30 * time.Second)
|
||||
defer timer.Stop()
|
||||
|
||||
ticker := time.NewTicker(100 * time.Millisecond)
|
||||
|
||||
@ -200,6 +200,24 @@ func (s *scenario) theAddressOfAccountHasMessagesInMailbox(address, username str
|
||||
})))
|
||||
}
|
||||
|
||||
func (s *scenario) theAddressOfAccountHasNoKeys(address, username string) error {
|
||||
userID := s.t.getUserID(username)
|
||||
addrID := s.t.getUserAddrID(userID, address)
|
||||
|
||||
keyIDs, err := s.t.api.GetAddressKeyIDs(userID, addrID)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, keyID := range keyIDs {
|
||||
if err := s.t.api.RemoveAddressKey(userID, addrID, keyID); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *scenario) userLogsInWithUsernameAndPassword(username, password string) error {
|
||||
userID, err := s.t.bridge.LoginFull(context.Background(), username, []byte(password), nil, nil)
|
||||
if err != nil {
|
||||
|
||||
Reference in New Issue
Block a user