Skip to content

Authenticate with OAuth 2.0 #109

Description

@asherp

Summary

Add support for authenticating with email providers using OAuth 2.0 instead of (or in addition to) plaintext username/password credentials for SMTP and IMAP.

Motivation

Major email providers (Gmail, Outlook/Microsoft 365, Yahoo) have deprecated or removed support for basic password authentication ("less secure apps") in favor of OAuth 2.0. To let users connect their existing mailboxes to nostr-mail without app-specific passwords, we need first-class OAuth 2.0 support.

Proposed scope

  • Implement the OAuth 2.0 authorization code flow for obtaining access/refresh tokens
  • Use OAuth bearer tokens (XOAUTH2 / SASL) when authenticating SMTP sending and IMAP fetching
  • Securely store and refresh tokens, handling token expiry transparently
  • Add provider presets for common providers (Gmail, Outlook) — see below
  • Update Settings UI to let users choose OAuth vs. password authentication and start the consent flow
  • Document configuration (client ID/secret, redirect URI, required scopes)

What is a provider preset?

A provider preset is a built-in configuration template for a specific email provider, so users don't have to manually enter all the technical OAuth/server details. Each provider requires a different set of values:

  • OAuth endpoints — the authorization URL and token URL (where the consent flow and token exchange happen)
  • Scopes — the permission strings that grant mail access (e.g. Gmail's https://mail.google.com/)
  • SMTP/IMAP server hostnames and ports — e.g. imap.gmail.com:993, smtp.gmail.com:465

A preset bundles all of these under a friendly name. Instead of looking up and typing in every field, the user picks "Gmail" from a dropdown and the app fills in the correct values, then launches the consent flow. A "Custom" option should remain as a fallback for advanced users or providers we haven't pre-configured.

Example shape:

const PROVIDER_PRESETS = {
  gmail: {
    name: "Gmail",
    authUrl: "https://accounts.google.com/o/oauth2/v2/auth",
    tokenUrl: "https://oauth2.googleapis.com/token",
    scopes: ["https://mail.google.com/"],
    imap: { host: "imap.gmail.com", port: 993 },
    smtp: { host: "smtp.gmail.com", port: 465 },
  },
  outlook: {
    name: "Outlook / Microsoft 365",
    authUrl: "https://login.microsoftonline.com/common/oauth2/v2.0/authorize",
    tokenUrl: "https://login.microsoftonline.com/common/oauth2/v2.0/token",
    scopes: ["https://outlook.office.com/IMAP.AccessAsUser.All"],
    imap: { host: "outlook.office365.com", port: 993 },
    smtp: { host: "smtp.office365.com", port: 587 },
  },
};

Open questions

  • Which providers should we support out of the box first?
  • How should client credentials be configured (bundled vs. user-provided)?
  • Where/how should tokens be stored given the cross-platform desktop + web targets?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions