diff --git a/CHANGELOG.md b/CHANGELOG.md index 449c721..6217094 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - Dashboard "Recent Processing Runs" table replaced with a per-account **Mailbox Status** view: each account now shows its last-check status (OK / Error / Pending), relative last-check time, any error message, and lifetime processed/failed counters. The noisy per-run table is gone; full activity history remains available on the Logs page. - Stats cards updated: "Emails Forwarded Today" → "Emails Processed" (all-time total from account records); "Errors" → "Accounts with Errors" (count of accounts currently showing an error). +### Fixed +- Provider logos now appear on the Mail Accounts page: `provider_name` is correctly saved when creating accounts via the provider wizard and propagated through backend/frontend schemas. +- Fetch-emails button now shows a text label ("Fetch"), a descriptive tooltip, a "Fetching…" loading state, and a brief green "Queued!" confirmation after the action completes. ## v0.3.2 (2026-03-28) diff --git a/backend/app/api/v1/endpoints/mail_accounts.py b/backend/app/api/v1/endpoints/mail_accounts.py index 3d870f4..34174a2 100644 --- a/backend/app/api/v1/endpoints/mail_accounts.py +++ b/backend/app/api/v1/endpoints/mail_accounts.py @@ -104,6 +104,7 @@ async def create_mail_account( check_interval_minutes=account_in.check_interval_minutes, max_emails_per_check=account_in.max_emails_per_check, delete_after_forward=account_in.delete_after_forward, + provider_name=account_in.provider_name, ) db.add(account) diff --git a/backend/app/models/schemas.py b/backend/app/models/schemas.py index 51d6fff..f630f60 100644 --- a/backend/app/models/schemas.py +++ b/backend/app/models/schemas.py @@ -113,6 +113,7 @@ class MailAccountBase(BaseModel): check_interval_minutes: int = Field(default=5, gt=0, le=1440) max_emails_per_check: int = Field(default=50, gt=0, le=1000) delete_after_forward: bool = True + provider_name: Optional[str] = Field(None, max_length=100) class MailAccountCreate(MailAccountBase): @@ -135,6 +136,7 @@ class MailAccountUpdate(BaseModel): check_interval_minutes: Optional[int] = Field(None, gt=0, le=1440) max_emails_per_check: Optional[int] = Field(None, gt=0, le=1000) delete_after_forward: Optional[bool] = None + provider_name: Optional[str] = Field(None, max_length=100) class MailAccountResponse(MailAccountBase): diff --git a/docs/TODO.md b/docs/TODO.md index 2a77b4e..167c304 100644 --- a/docs/TODO.md +++ b/docs/TODO.md @@ -5,6 +5,9 @@ Comprehensive task breakdown for repository improvements and production readines ## ✅ Recently Completed - [x] **Dashboard redesign**: Replaced noisy "Recent Processing Runs" table with a per-account "Mailbox Status" view showing last-check status (OK/Error/Pending), relative timestamp, error messages, and lifetime counters. Stats cards updated to show all-time processed count and accounts-with-errors count. +- [x] **Provider logos now saved on account creation**: `provider_name` field added to `MailAccountCreate` and `MailAccountUpdate` schemas (backend and frontend). `ProviderWizard` now passes `provider_name` in its `onSelect` callback; `AddMailAccountModal` stores it so logos are displayed correctly on the accounts page. +- [x] **Fetch button UX improvements**: The "fetch emails" button on the accounts page now shows a "Fetch" text label for clarity, a tooltip explaining its purpose, a spinning "Fetching…" state during the API call, and a brief green "Queued!" confirmation after success. + - [x] **Pull Now**: Added "Pull Now" button on Accounts page that immediately queues a `process_mail_account` Celery task via `POST /mail-accounts/{id}/pull-now`. Button shows spinner while in flight and is disabled for inactive accounts. - [x] Fixed 21 mypy type errors: `Column[T]` vs native type mismatches in `notification_service.py`, `mail_processor.py`, `auth.py`, `tasks.py`, `providers.py`, `mail_accounts.py`, and `main.py` (`lifespan` parameter rename). - [x] **Provider logos rework**: Logos now displayed as full-width banner strips at the top of each account card using `next/image fill + object-contain`. Handles all aspect ratios (1:1 square to 6:1 wordmark) without distortion. Proton Mail added. diff --git a/frontend/src/app/accounts/page.tsx b/frontend/src/app/accounts/page.tsx index 6e6aae5..714aa91 100644 --- a/frontend/src/app/accounts/page.tsx +++ b/frontend/src/app/accounts/page.tsx @@ -53,6 +53,7 @@ export default function AccountsPage() { const [isModalOpen, setIsModalOpen] = useState(false); const [editingAccount, setEditingAccount] = useState(null); const [pullingIds, setPullingIds] = useState>(new Set()); + const [successIds, setSuccessIds] = useState>(new Set()); const queryClient = useQueryClient(); const { data: accounts, isLoading } = useQuery({ @@ -101,6 +102,14 @@ export default function AccountsPage() { setPullingIds((prev) => new Set(prev).add(id)); try { await mailAccountsApi.pullNow(id); + setSuccessIds((prev) => new Set(prev).add(id)); + setTimeout(() => { + setSuccessIds((prev) => { + const next = new Set(prev); + next.delete(id); + return next; + }); + }, 2000); } catch { alert('Failed to queue pull'); } finally { @@ -227,11 +236,22 @@ export default function AccountsPage() {