Fix: IMAP Sent-Ordner — echten Namen aus LIST-Antwort extrahieren (INBOX.Sent)
This commit is contained in:
parent
31fae63658
commit
4c6dd07c31
1 changed files with 25 additions and 11 deletions
|
|
@ -10,13 +10,16 @@ from email.utils import formataddr
|
|||
from datetime import datetime
|
||||
from typing import List, Optional
|
||||
|
||||
import logging
|
||||
|
||||
from fastapi import APIRouter, Depends, HTTPException
|
||||
from pydantic import BaseModel
|
||||
|
||||
from auth import require_admin
|
||||
from database import db
|
||||
|
||||
router = APIRouter()
|
||||
router = APIRouter()
|
||||
_log = logging.getLogger(__name__)
|
||||
|
||||
_SMTP_HOST = os.getenv("SMTP_HOST", "mail.your-server.de")
|
||||
_SMTP_PORT = int(os.getenv("SMTP_PORT", "587"))
|
||||
|
|
@ -45,29 +48,40 @@ _SENT_CANDIDATES = ["Sent", "Sent Messages", "Sent Items", "INBOX.Sent", "Gesend
|
|||
def _imap_save_sent(msg_bytes: bytes, account: str):
|
||||
acc = _ACCOUNTS.get(account) or _ACCOUNTS["partner"]
|
||||
if not acc["user"] or not acc["pass"]:
|
||||
_log.warning("IMAP: Account '%s' nicht konfiguriert, überspringe.", account)
|
||||
return
|
||||
try:
|
||||
ctx = ssl.create_default_context()
|
||||
with imaplib.IMAP4_SSL(_IMAP_HOST, _IMAP_PORT, ssl_context=ctx) as imap:
|
||||
imap.login(acc["user"], acc["pass"])
|
||||
# Sent-Ordner finden
|
||||
_, raw_folders = imap.list()
|
||||
available = [f.decode(errors="replace") for f in (raw_folders or [])]
|
||||
_log.info("IMAP Ordner (%s): %s", account, available)
|
||||
|
||||
# Echten Ordnernamen aus LIST-Antwort extrahieren
|
||||
# Format: '(\Flags) "." INBOX.Sent' → letztes Token
|
||||
folder = None
|
||||
_, folders = imap.list()
|
||||
available = [f.decode() for f in (folders or [])]
|
||||
for candidate in _SENT_CANDIDATES:
|
||||
if any(candidate.lower() in f.lower() for f in available):
|
||||
folder = candidate
|
||||
for line in available:
|
||||
name = line.rsplit('"." ', 1)[-1].strip().strip('"')
|
||||
for candidate in _SENT_CANDIDATES:
|
||||
if candidate.lower() in name.lower():
|
||||
folder = name
|
||||
break
|
||||
if folder:
|
||||
break
|
||||
if not folder:
|
||||
folder = "Sent" # Fallback: anlegen lassen
|
||||
imap.append(
|
||||
folder = "INBOX.Sent"
|
||||
_log.info("IMAP: speichere in Ordner '%s' (%s)", folder, account)
|
||||
|
||||
typ, data = imap.append(
|
||||
folder,
|
||||
r"\Seen",
|
||||
imaplib.Time2Internaldate(datetime.now().timestamp()),
|
||||
msg_bytes,
|
||||
)
|
||||
except Exception:
|
||||
pass # Nicht blockieren wenn IMAP fehlschlägt
|
||||
_log.info("IMAP append: %s %s", typ, data)
|
||||
except Exception as e:
|
||||
_log.error("IMAP Sent-Speicherung fehlgeschlagen (%s): %s", account, e)
|
||||
|
||||
|
||||
def _build_message(to: str, subject: str, body: str, account: str) -> MIMEMultipart:
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue