{
  "schemaVersion": "1.0",
  "item": {
    "slug": "imap-idle",
    "name": "Imap Idle Review",
    "source": "tencent",
    "type": "skill",
    "category": "效率提升",
    "sourceUrl": "https://clawhub.ai/topitip/imap-idle",
    "canonicalUrl": "https://clawhub.ai/topitip/imap-idle",
    "targetPlatform": "OpenClaw"
  },
  "install": {
    "downloadMode": "redirect",
    "downloadUrl": "/downloads/imap-idle",
    "sourceDownloadUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=imap-idle",
    "sourcePlatform": "tencent",
    "targetPlatform": "OpenClaw",
    "installMethod": "Manual import",
    "extraction": "Extract archive",
    "prerequisites": [
      "OpenClaw"
    ],
    "packageFormat": "ZIP package",
    "includedAssets": [
      "CHANGELOG.md",
      "README.md",
      "SECURITY.md",
      "SKILL.md",
      "scripts/listener.py",
      "scripts/listener_old.py"
    ],
    "primaryDoc": "SKILL.md",
    "quickSetup": [
      "Download the package from Yavira.",
      "Extract the archive and review SKILL.md first.",
      "Import or place the package into your OpenClaw setup."
    ],
    "agentAssist": {
      "summary": "Hand the extracted package to your coding agent with a concrete install brief instead of figuring it out manually.",
      "steps": [
        "Download the package from Yavira.",
        "Extract it into a folder your agent can access.",
        "Paste one of the prompts below and point your agent at the extracted folder."
      ],
      "prompts": [
        {
          "label": "New install",
          "body": "I downloaded a skill package from Yavira. Read SKILL.md from the extracted folder and install it by following the included instructions. Then review README.md for any prerequisites, environment setup, or post-install checks. Tell me what you changed and call out any manual steps you could not complete."
        },
        {
          "label": "Upgrade existing",
          "body": "I downloaded an updated skill package from Yavira. Read SKILL.md from the extracted folder, compare it with my current installation, and upgrade it while preserving any custom configuration unless the package docs explicitly say otherwise. Then review README.md for any prerequisites, environment setup, or post-install checks. Summarize what changed and any follow-up checks I should run."
        }
      ]
    },
    "sourceHealth": {
      "source": "tencent",
      "status": "healthy",
      "reason": "direct_download_ok",
      "recommendedAction": "download",
      "checkedAt": "2026-04-23T16:43:11.935Z",
      "expiresAt": "2026-04-30T16:43:11.935Z",
      "httpStatus": 200,
      "finalUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=4claw-imageboard",
      "contentType": "application/zip",
      "probeMethod": "head",
      "details": {
        "probeUrl": "https://wry-manatee-359.convex.site/api/v1/download?slug=4claw-imageboard",
        "contentDisposition": "attachment; filename=\"4claw-imageboard-1.0.1.zip\"",
        "redirectLocation": null,
        "bodySnippet": null
      },
      "scope": "source",
      "summary": "Source download looks usable.",
      "detail": "Yavira can redirect you to the upstream package for this source.",
      "primaryActionLabel": "Download for OpenClaw",
      "primaryActionHref": "/downloads/imap-idle"
    },
    "validation": {
      "installChecklist": [
        "Use the Yavira download entry.",
        "Review SKILL.md after the package is downloaded.",
        "Confirm the extracted package contains the expected setup assets."
      ],
      "postInstallChecks": [
        "Confirm the extracted package includes the expected docs or setup files.",
        "Validate the skill or prompts are available in your target agent workspace.",
        "Capture any manual follow-up steps the agent could not complete."
      ]
    },
    "downloadPageUrl": "https://openagent3.xyz/downloads/imap-idle",
    "agentPageUrl": "https://openagent3.xyz/skills/imap-idle/agent",
    "manifestUrl": "https://openagent3.xyz/skills/imap-idle/agent.json",
    "briefUrl": "https://openagent3.xyz/skills/imap-idle/agent.md"
  },
  "agentAssist": {
    "summary": "Hand the extracted package to your coding agent with a concrete install brief instead of figuring it out manually.",
    "steps": [
      "Download the package from Yavira.",
      "Extract it into a folder your agent can access.",
      "Paste one of the prompts below and point your agent at the extracted folder."
    ],
    "prompts": [
      {
        "label": "New install",
        "body": "I downloaded a skill package from Yavira. Read SKILL.md from the extracted folder and install it by following the included instructions. Then review README.md for any prerequisites, environment setup, or post-install checks. Tell me what you changed and call out any manual steps you could not complete."
      },
      {
        "label": "Upgrade existing",
        "body": "I downloaded an updated skill package from Yavira. Read SKILL.md from the extracted folder, compare it with my current installation, and upgrade it while preserving any custom configuration unless the package docs explicitly say otherwise. Then review README.md for any prerequisites, environment setup, or post-install checks. Summarize what changed and any follow-up checks I should run."
      }
    ]
  },
  "documentation": {
    "source": "clawhub",
    "primaryDoc": "SKILL.md",
    "sections": [
      {
        "title": "IMAP IDLE Listener",
        "body": "Event-driven email notifications for OpenClaw using IMAP IDLE protocol."
      },
      {
        "title": "What This Does",
        "body": "Replaces polling-based email checks with push notifications:\n\nBefore (polling):\n\nCron job checks email every hour\n16-24 checks per day\nUp to 1 hour delay for new emails\nToken burn on empty checks\n\nAfter (IMAP IDLE):\n\nPersistent connection to IMAP server\nServer pushes notification when new mail arrives\n<1 second notification latency\nZero tokens while waiting"
      },
      {
        "title": "1. Enable OpenClaw Webhooks",
        "body": "Edit ~/.openclaw/openclaw.json:\n\n{\n  \"hooks\": {\n    \"enabled\": true,\n    \"token\": \"generate-secure-random-token-here\",\n    \"path\": \"/hooks\"\n  }\n}\n\nRestart gateway: openclaw gateway restart"
      },
      {
        "title": "2. Install Dependencies",
        "body": "pip3 install imapclient --user --break-system-packages\n\nOptional but recommended: Install keyring for secure password storage:\n\npip3 install keyring --user --break-system-packages\n\nWith keyring, passwords are stored in your system's secure keychain (macOS Keychain, GNOME Keyring, etc.) instead of plain text in config files."
      },
      {
        "title": "3. Run Setup",
        "body": "./imap-idle setup\n\nFollow the interactive wizard to configure:\n\nIMAP account(s) (host, port, username, password)\nOpenClaw webhook URL and token\nLog file location"
      },
      {
        "title": "4. Start Listener",
        "body": "./imap-idle start\n\nVerify it's running:\n\n./imap-idle status\n./imap-idle logs"
      },
      {
        "title": "5. Test",
        "body": "Send yourself an email. You should see:\n\nLog entry in listener logs\nOpenClaw wakes instantly\nEmail processed in main session"
      },
      {
        "title": "CLI Commands",
        "body": "imap-idle start    # Start listener in background\nimap-idle stop     # Stop listener\nimap-idle restart  # Restart listener\nimap-idle status   # Check if running\nimap-idle logs     # Show recent logs (default: 50 lines)\nimap-idle logs N   # Show last N lines\nimap-idle setup    # Run interactive setup wizard"
      },
      {
        "title": "Configuration",
        "body": "Config file: ~/.openclaw/imap-idle.json\n\n{\n  \"accounts\": [\n    {\n      \"host\": \"mail.example.com\",\n      \"port\": 993,\n      \"username\": \"user@example.com\",\n      \"password\": \"password\",\n      \"ssl\": true\n    }\n  ],\n  \"webhook_url\": \"http://127.0.0.1:18789/hooks/wake\",\n  \"webhook_token\": \"your-webhook-token\",\n  \"log_file\": \"~/.openclaw/logs/imap-idle.log\",\n  \"idle_timeout\": 300,\n  \"reconnect_interval\": 900,\n  \"debounce_seconds\": 10\n}\n\nFields:\n\naccounts - Array of IMAP accounts to monitor\nwebhook_url - OpenClaw webhook endpoint\nwebhook_token - Webhook authentication token (from openclaw.json)\nlog_file - Path to log file (null for stdout)\nidle_timeout - IDLE check timeout in seconds (default: 300 = 5 min)\nreconnect_interval - Full reconnect interval in seconds (default: 900 = 15 min)\ndebounce_seconds - Batch events for N seconds before webhook (default: 10 sec)"
      },
      {
        "title": "Secure Password Storage (Keyring)",
        "body": "🔐 Recommended: Store passwords in system keychain instead of config file."
      },
      {
        "title": "Setup with Keyring",
        "body": "When you run ./imap-idle setup, the wizard will ask if you want to use keyring. If you say yes:\n\nPasswords are stored in your system's secure keychain\nConfig file only contains usernames (no passwords)\nKeyring uses OS-level encryption"
      },
      {
        "title": "Manual Keyring Setup",
        "body": "If you already have a config with plain text passwords, migrate to keyring:\n\n# Install keyring\npip3 install keyring --user --break-system-packages\n\n# Store password for each account\npython3 -c \"\nimport keyring, getpass\nusername = 'user@example.com'\npassword = getpass.getpass(f'Password for {username}: ')\nkeyring.set_password('imap-idle', username, password)\n\"\n\n# Remove password from config\n# Edit ~/.openclaw/imap-idle.json and remove \"password\" field"
      },
      {
        "title": "How Keyring Works",
        "body": "The listener automatically tries keyring first, then falls back to config:\n\nTry keyring.get_password('imap-idle', username)\nIf not found, use config['password']\nIf still no password, abort connection"
      },
      {
        "title": "Security Benefits",
        "body": "✅ No plain text passwords in config files\n✅ OS-level encryption (macOS Keychain, GNOME Keyring, Windows Credential Manager)\n✅ Reduces VirusTotal false positives\n✅ Better security audit trail"
      },
      {
        "title": "How It Works",
        "body": "Connect: Opens persistent IMAP connection per account\nIDLE: Enters IDLE mode (server will push notifications)\nWait: Blocks until server sends \"new mail\" notification\nFetch: Retrieves new email headers (From, Subject, body preview)\nQueue: Adds event to debounce buffer (batches for 10 seconds)\nWebhook: Sends batched events via webhook (single or grouped)\nResume: Re-enters IDLE mode\n\nKey Implementation Details:\n\nDebouncing: Batches emails for 10 seconds before webhook to prevent flooding during spikes (e.g., GitHub mention storms)\nSmart Batching: Single email → full details, multiple emails → grouped summary with counts\nUID Tracking: Tracks last processed message UID per account to prevent duplicate webhooks\nKeep-alive: IDLE timeout every 5 minutes, sends NOOP command\nReconnect: Full reconnect every 15 minutes to prevent stale connections\nThreading: One thread per account for concurrent monitoring\nError handling: Exponential backoff (5s → 300s) on connection failures"
      },
      {
        "title": "Systemd Service (Optional)",
        "body": "For automatic startup on boot:\n\nGenerate service file:\n\nskill_dir=\"$(pwd)\"\nlistener_script=\"$skill_dir/scripts/listener.py\"\nconfig_file=\"$HOME/.openclaw/imap-idle.json\"\nlog_file=\"$HOME/.openclaw/logs/imap-idle.log\"\nlog_dir=\"$(dirname \"$log_file\")\"\n\nsed -e \"s|%USER%|$USER|g\" \\\n    -e \"s|%PYTHON%|$(which python3)|g\" \\\n    -e \"s|%LISTENER_SCRIPT%|$listener_script|g\" \\\n    -e \"s|%CONFIG_FILE%|$config_file|g\" \\\n    -e \"s|%LOG_FILE%|$log_file|g\" \\\n    -e \"s|%LOG_DIR%|$log_dir|g\" \\\n    imap-idle.service.template > imap-idle.service\n\nInstall service:\n\nsudo cp imap-idle.service /etc/systemd/system/\nsudo systemctl daemon-reload\nsudo systemctl enable imap-idle\nsudo systemctl start imap-idle\n\nCheck status:\n\nsudo systemctl status imap-idle\nsudo journalctl -u imap-idle -f"
      },
      {
        "title": "Troubleshooting",
        "body": "Listener won't start:\n\nCheck config file exists: cat ~/.openclaw/imap-idle.json\nVerify imapclient installed: python3 -c \"import imapclient\"\nCheck logs: imap-idle logs\n\nDuplicate webhooks:\n\nFixed in v2 - uses UID tracking to prevent duplicates\nCheck logs for \"UID tracking\" messages\n\nConnection drops:\n\nIncrease reconnect_interval in config\nCheck IMAP server allows IDLE (most do)\nVerify firewall allows persistent connections\n\nNo webhooks triggering:\n\nTest webhook manually:\ncurl -X POST http://127.0.0.1:18789/hooks/wake \\\n  -H \"Authorization: Bearer YOUR_TOKEN\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"text\": \"test\", \"mode\": \"now\"}'\n\n\nCheck OpenClaw config: hooks.enabled: true\nVerify token matches in both configs"
      },
      {
        "title": "Removing Polling",
        "body": "Once IMAP IDLE is working, remove old polling cron jobs:\n\n# List cron jobs\nopenclaw cron list\n\n# Remove email check job\nopenclaw cron remove <job-id>"
      },
      {
        "title": "Token Savings",
        "body": "Before:\n\n16-24 email checks per day\nEach check = ~500-1000 tokens (even if no new mail)\nTotal: ~8,000-24,000 tokens/day for email monitoring\n\nAfter:\n\n0 tokens while waiting\nTokens only spent when email actually arrives\n90%+ reduction in email-related token usage"
      },
      {
        "title": "Credits",
        "body": "Inspired by @claude-event-listeners' critique on Moltbook about polling vs event-driven architecture.\n\nImplementation details from real-world debugging documented in Moltbook post \"Event-Driven Email: From Polling to IMAP IDLE (with code)\"."
      }
    ],
    "body": "IMAP IDLE Listener\n\nEvent-driven email notifications for OpenClaw using IMAP IDLE protocol.\n\nWhat This Does\n\nReplaces polling-based email checks with push notifications:\n\nBefore (polling):\n\nCron job checks email every hour\n16-24 checks per day\nUp to 1 hour delay for new emails\nToken burn on empty checks\n\nAfter (IMAP IDLE):\n\nPersistent connection to IMAP server\nServer pushes notification when new mail arrives\n<1 second notification latency\nZero tokens while waiting\nQuick Start\n1. Enable OpenClaw Webhooks\n\nEdit ~/.openclaw/openclaw.json:\n\n{\n  \"hooks\": {\n    \"enabled\": true,\n    \"token\": \"generate-secure-random-token-here\",\n    \"path\": \"/hooks\"\n  }\n}\n\n\nRestart gateway: openclaw gateway restart\n\n2. Install Dependencies\npip3 install imapclient --user --break-system-packages\n\n\nOptional but recommended: Install keyring for secure password storage:\n\npip3 install keyring --user --break-system-packages\n\n\nWith keyring, passwords are stored in your system's secure keychain (macOS Keychain, GNOME Keyring, etc.) instead of plain text in config files.\n\n3. Run Setup\n./imap-idle setup\n\n\nFollow the interactive wizard to configure:\n\nIMAP account(s) (host, port, username, password)\nOpenClaw webhook URL and token\nLog file location\n4. Start Listener\n./imap-idle start\n\n\nVerify it's running:\n\n./imap-idle status\n./imap-idle logs\n\n5. Test\n\nSend yourself an email. You should see:\n\nLog entry in listener logs\nOpenClaw wakes instantly\nEmail processed in main session\nCLI Commands\nimap-idle start    # Start listener in background\nimap-idle stop     # Stop listener\nimap-idle restart  # Restart listener\nimap-idle status   # Check if running\nimap-idle logs     # Show recent logs (default: 50 lines)\nimap-idle logs N   # Show last N lines\nimap-idle setup    # Run interactive setup wizard\n\nConfiguration\n\nConfig file: ~/.openclaw/imap-idle.json\n\n{\n  \"accounts\": [\n    {\n      \"host\": \"mail.example.com\",\n      \"port\": 993,\n      \"username\": \"user@example.com\",\n      \"password\": \"password\",\n      \"ssl\": true\n    }\n  ],\n  \"webhook_url\": \"http://127.0.0.1:18789/hooks/wake\",\n  \"webhook_token\": \"your-webhook-token\",\n  \"log_file\": \"~/.openclaw/logs/imap-idle.log\",\n  \"idle_timeout\": 300,\n  \"reconnect_interval\": 900,\n  \"debounce_seconds\": 10\n}\n\n\nFields:\n\naccounts - Array of IMAP accounts to monitor\nwebhook_url - OpenClaw webhook endpoint\nwebhook_token - Webhook authentication token (from openclaw.json)\nlog_file - Path to log file (null for stdout)\nidle_timeout - IDLE check timeout in seconds (default: 300 = 5 min)\nreconnect_interval - Full reconnect interval in seconds (default: 900 = 15 min)\ndebounce_seconds - Batch events for N seconds before webhook (default: 10 sec)\nSecure Password Storage (Keyring)\n\n🔐 Recommended: Store passwords in system keychain instead of config file.\n\nSetup with Keyring\n\nWhen you run ./imap-idle setup, the wizard will ask if you want to use keyring. If you say yes:\n\nPasswords are stored in your system's secure keychain\nConfig file only contains usernames (no passwords)\nKeyring uses OS-level encryption\nManual Keyring Setup\n\nIf you already have a config with plain text passwords, migrate to keyring:\n\n# Install keyring\npip3 install keyring --user --break-system-packages\n\n# Store password for each account\npython3 -c \"\nimport keyring, getpass\nusername = 'user@example.com'\npassword = getpass.getpass(f'Password for {username}: ')\nkeyring.set_password('imap-idle', username, password)\n\"\n\n# Remove password from config\n# Edit ~/.openclaw/imap-idle.json and remove \"password\" field\n\nHow Keyring Works\n\nThe listener automatically tries keyring first, then falls back to config:\n\nTry keyring.get_password('imap-idle', username)\nIf not found, use config['password']\nIf still no password, abort connection\nSecurity Benefits\n✅ No plain text passwords in config files\n✅ OS-level encryption (macOS Keychain, GNOME Keyring, Windows Credential Manager)\n✅ Reduces VirusTotal false positives\n✅ Better security audit trail\nHow It Works\nConnect: Opens persistent IMAP connection per account\nIDLE: Enters IDLE mode (server will push notifications)\nWait: Blocks until server sends \"new mail\" notification\nFetch: Retrieves new email headers (From, Subject, body preview)\nQueue: Adds event to debounce buffer (batches for 10 seconds)\nWebhook: Sends batched events via webhook (single or grouped)\nResume: Re-enters IDLE mode\n\nKey Implementation Details:\n\nDebouncing: Batches emails for 10 seconds before webhook to prevent flooding during spikes (e.g., GitHub mention storms)\nSmart Batching: Single email → full details, multiple emails → grouped summary with counts\nUID Tracking: Tracks last processed message UID per account to prevent duplicate webhooks\nKeep-alive: IDLE timeout every 5 minutes, sends NOOP command\nReconnect: Full reconnect every 15 minutes to prevent stale connections\nThreading: One thread per account for concurrent monitoring\nError handling: Exponential backoff (5s → 300s) on connection failures\nSystemd Service (Optional)\n\nFor automatic startup on boot:\n\nGenerate service file:\nskill_dir=\"$(pwd)\"\nlistener_script=\"$skill_dir/scripts/listener.py\"\nconfig_file=\"$HOME/.openclaw/imap-idle.json\"\nlog_file=\"$HOME/.openclaw/logs/imap-idle.log\"\nlog_dir=\"$(dirname \"$log_file\")\"\n\nsed -e \"s|%USER%|$USER|g\" \\\n    -e \"s|%PYTHON%|$(which python3)|g\" \\\n    -e \"s|%LISTENER_SCRIPT%|$listener_script|g\" \\\n    -e \"s|%CONFIG_FILE%|$config_file|g\" \\\n    -e \"s|%LOG_FILE%|$log_file|g\" \\\n    -e \"s|%LOG_DIR%|$log_dir|g\" \\\n    imap-idle.service.template > imap-idle.service\n\nInstall service:\nsudo cp imap-idle.service /etc/systemd/system/\nsudo systemctl daemon-reload\nsudo systemctl enable imap-idle\nsudo systemctl start imap-idle\n\nCheck status:\nsudo systemctl status imap-idle\nsudo journalctl -u imap-idle -f\n\nTroubleshooting\n\nListener won't start:\n\nCheck config file exists: cat ~/.openclaw/imap-idle.json\nVerify imapclient installed: python3 -c \"import imapclient\"\nCheck logs: imap-idle logs\n\nDuplicate webhooks:\n\nFixed in v2 - uses UID tracking to prevent duplicates\nCheck logs for \"UID tracking\" messages\n\nConnection drops:\n\nIncrease reconnect_interval in config\nCheck IMAP server allows IDLE (most do)\nVerify firewall allows persistent connections\n\nNo webhooks triggering:\n\nTest webhook manually:\ncurl -X POST http://127.0.0.1:18789/hooks/wake \\\n  -H \"Authorization: Bearer YOUR_TOKEN\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"text\": \"test\", \"mode\": \"now\"}'\n\nCheck OpenClaw config: hooks.enabled: true\nVerify token matches in both configs\nRemoving Polling\n\nOnce IMAP IDLE is working, remove old polling cron jobs:\n\n# List cron jobs\nopenclaw cron list\n\n# Remove email check job\nopenclaw cron remove <job-id>\n\nToken Savings\n\nBefore:\n\n16-24 email checks per day\nEach check = ~500-1000 tokens (even if no new mail)\nTotal: ~8,000-24,000 tokens/day for email monitoring\n\nAfter:\n\n0 tokens while waiting\nTokens only spent when email actually arrives\n90%+ reduction in email-related token usage\nCredits\n\nInspired by @claude-event-listeners' critique on Moltbook about polling vs event-driven architecture.\n\nImplementation details from real-world debugging documented in Moltbook post \"Event-Driven Email: From Polling to IMAP IDLE (with code)\"."
  },
  "trust": {
    "sourceLabel": "tencent",
    "provenanceUrl": "https://clawhub.ai/topitip/imap-idle",
    "publisherUrl": "https://clawhub.ai/topitip/imap-idle",
    "owner": "topitip",
    "version": "1.4.0",
    "license": null,
    "verificationStatus": "Indexed source record"
  },
  "links": {
    "detailUrl": "https://openagent3.xyz/skills/imap-idle",
    "downloadUrl": "https://openagent3.xyz/downloads/imap-idle",
    "agentUrl": "https://openagent3.xyz/skills/imap-idle/agent",
    "manifestUrl": "https://openagent3.xyz/skills/imap-idle/agent.json",
    "briefUrl": "https://openagent3.xyz/skills/imap-idle/agent.md"
  }
}