The instant unfiled-email count. Asks which user’s inbox first (because email is personal), then fetches the Merus Messages index, filters to unfiled, and prints the list with date + sender + subject. Under five seconds. No AI, no body fetches, no attachment downloads. The email-side companion to any-new-mail.
At the prompt:
aaicase> check my email
aaicase> check messages
aaicase> any new email
aaicase> email inbox
The skill asks which user’s inbox to look at, fetches that user’s unfiled emails, and prints up to 30 of them with date + sender + subject + attachment indicator. If the inbox is clear, it says so and stops. If there are items, the last line says: “Say process messages to file these to cases.”
It’s the polling skill on the email side — ambient, repeatable, instant. The same intent as any new mail, against a different Merus queue.
Pulled live from /users/index, the user list is shown as numbered options:
Which user's email inbox should I check?
1. Sample Firm Admin (SFA) — admin@example.com
2. Sample Attorney (SA) — attorney@aai.dev
3. Sample Associate (SC) — associate@example.com
4. Sample Paralegal (SP) — paralegal@example.com
Type a number, name, or initials (e.g., "3", "Sample Associate", or "SA")
The attorney’s response can be a number, a first name, a last name, or initials — the skill matches case-insensitively against the catalog. If the original command included a hint (“check the associate’s messages,” “check email for SA”), the skill matches that hint against the catalog and skips the prompt.
The chosen user persists for the session. Subsequent process messages or check my email commands default to the same user unless the attorney specifies otherwise.
For a message to count as unfiled, two conditions both apply:
case_file_id === null — the email hasn’t been linked to a casedeleted === false — not in the trashThen a third condition narrows to the selected user’s inbox:
recipient_header_to (received items), ORsender_header (sent items the user wrote but didn’t file)For the “unfiled emails to file” use case — which is the dominant one — that’s typically messages received by the selected user. The skill counts both sent and received because both can need filing.
Two API calls in sequence:
node bin/merus-fetch.mjs /users/index → user catalog (for the picker)
node bin/merus-fetch.mjs /messages/index → all messages
The first call only happens if the user wasn’t already chosen (or the attorney didn’t hint at one). The second call fetches the global Messages index and the skill filters client-side. No temp directory, no per-message detail fetches, no body fetches via /messages/view.
Total bounded by Merus latency. Typically 2–4 seconds for the messages fetch alone, plus 1–2 seconds for the users fetch if needed.
The skill explicitly does not:
/messages/view?message_id=... to fetch full body content (that’s process messages’ job)The whole point is the speed contract: under 5 seconds, no AI tokens, no inference. The skill is purely “how many emails, what do their headers say, in date order.” If you want body content, use process messages — that’s the heavy companion.
This is the same speed/AI contract as any new mail and status. The three together form the “instant tier” of AAI — deterministic counts you can run dozens of times a day without thinking about cost.
Each line shows a paperclip indicator if the message has attachments:
[MSG-ID] | 2026-05-26 | adjuster@example.com | RE: Roe TD demand [📎]
The indicator is computed from the upload_id field on the message — if it’s populated (array with at least one item, or object with keys), the paperclip appears. The skill doesn’t download or read the attachments; it just notes their presence.
This matters for triage. Emails with attachments are usually the substantive ones (documents to file, reports to review); pure-text emails are often coordination messages that file in seconds. Knowing which is which before running process-messages helps the attorney decide how much time the batch will take.
Once the attorney picks a user, that user becomes the session default. Subsequent runs of:
… both default to the same user. The attorney can override at any time by specifying (“check email for SA”), and the override sticks for the rest of the session.
The persistence is in-session only — restarting aaicase resets the choice and the next run asks again. This is intentional: email is personal, and the prompt is a security check against a paralegal or covering attorney accidentally walking through someone else’s inbox.
| check my email | any new mail? | |
|---|---|---|
| Source | /messages/index — emails received by firm | /uploads/index — PDFs uploaded/scanned to firm |
| Per-user filter | Yes — asks which user | No — firm-wide queue |
| Counts | Unfiled messages (case_file_id null + not deleted) | Orphan uploads (no case + no activity) |
| Followed by | process messages | process mail |
The two queues are deliberately separate because the data is separate. A firm might have 12 unprocessed uploads (mail) and 0 unfiled emails, or 0 mail and 30 emails. Running “any new mail” doesn’t check email; running “check my email” doesn’t check mail.
| check my email | process messages | |
|---|---|---|
| Time | Under 5 seconds | ~10 minutes for a typical batch |
| Reads email body | No — metadata only | Yes — full HTML body via /messages/view, plus thread context |
| Reads attachments | No — just notes their presence | Yes — PDF natively via Claude vision |
| Writes | No | Yes — creates activities, links emails to cases |
| Cost | Effectively zero | ~a small amount of API budget per email (more with attachments) |
| Question answered | “Is there anything?” | “What is it and where does it go?” |
The polling pattern: run check my email throughout the day; when something non-trivial shows up, run process messages to file the batch.
With unfiled emails:
Which user's email inbox should I check?
1. Sample Firm Admin (SFA) — admin@example.com
2. Sample Attorney (SA) — attorney@aai.dev
3. Sample Associate (SC) — associate@example.com
4. Sample Paralegal (SP) — paralegal@example.com
> 3
8 unfiled emails for associate@example.com:
[MSG-1] | 2026-05-26 | adjuster@example.com | RE: Roe TD demand response [📎]
[MSG-2] | 2026-05-26 | dr.sample@example.com | QME report for Doe — see attached [📎]
[MSG-3] | 2026-05-26 | defense@samplelaw.com | DOR — Sample v. Sample Co.
[MSG-4] | 2026-05-25 | clerk@anaheim.wcab.ca.gov | Hearing continued — Doe MSC
[MSG-5] | 2026-05-25 | copyservice@example.com | Records delivered for Sample [📎]
[MSG-6] | 2026-05-24 | client.doe@example.com | Question about my case
[MSG-7] | 2026-05-23 | adjuster@example.com | UR decision — Roe physical therapy
[MSG-8] | 2026-05-23 | defense@samplelaw.com | Notice of appearance — Sample
Say "process messages" to file these to cases.
(generated in 3.1s)
With a clear inbox:
No unfiled emails for associate@example.com. Inbox is clear.
(generated in 2.7s)
The Merus Messages indexer may have caching latency — emails landing seconds before the run may not be in /messages/index yet. Wait 30 seconds and re-run.
The list is pulled live from /users/index — everyone with an email and a name. Firms with former employees still in the user table will see those names. The skill doesn’t filter on active/inactive status; that’s a firm-admin task in Merus settings.
It’s unfiled and will stay unfiled until someone files it. Either run process messages or file in the Merus UI manually. Check-email is read-only; it never closes anything.
The upload_id field on the message record is the source. If Merus didn’t populate it correctly (rare but happens with some integrations), the paperclip won’t show. Run process messages on that specific message to see the attachments; it does a per-message fetch that’s authoritative.
Re-run check my email with a different hint (“check email for SA”), or restart aaicase to reset the session default.
The display is capped at 30 with a “... and N more” line at the bottom. The total count in the first line is accurate; the list itself is truncated for readability. Run process messages to walk through all of them.
Part of AAI for MerusCase — code-guarded AI case intelligence for California Workers’ Comp attorneys.