پرش به مستندات
CLI

فرستادن و ردیابی ایمیل

با فرمان‌های `emails` نامه را بفرستید، دسته‌ای بفرستید، ترجمه، زمان‌بندی و لغو کنید، سپس تحویل، باز شدن‌ها و کلیک‌هایش را با `tracking` دنبال کنید.

نمای کلی

فضای نام emails همان API فرستادن به‌صورت فرمان است، یک فرمان برای هر متد openemail.emails در SDK. هر کدام یک نقطهٔ پایانی را فرا می‌خواند و آنچه برمی‌گرداند را چاپ می‌کند. فضای نام tracking باز شدن‌ها و کلیک‌های نامه‌هایی را که فرستاده‌اید می‌خواند. openemail email هم به جای openemail emails کار می‌کند.

هر فرمان اینجا به یک ورود نیاز دارد، با مرورگر یا یک کلید API، و به یکی از دو دامنهٔ مجوز: emails:send برای فرستادن، ترجمه، لغو و زمان‌بندی دوباره، و emails:read برای هر چیزی که فقط می‌خواند.

از کدام فرمان فرستادن استفاده کنید

openemail send فرمان دست‌نوشتهٔ صفحهٔ نامه است و از طریق emails send می‌فرستد. برای کسی ساخته شده که پای ترمینال است: وقتی --from را نگذارید نشانی فرستنده را انتخاب می‌کند، متن را از یک فایل، stdin یا ویرایشگرتان می‌خواند، فایل‌ها را با مسیرشان پیوست می‌کند و پیش از فرستادن هر چیزی خلاصه‌ای برای تأیید نشان می‌دهد. openemail emails send بدنهٔ درخواست را به‌صورت پرچم می‌گیرد، یک پرچم برای هر فیلد، و چیزی نمی‌پرسد، که برای اسکریپتی مناسب است که دقیقاً می‌داند چه می‌فرستد.

sendemails send
--from <address>الزامی است، مانند --to، مگر اینکه --data آن را داشته باشد. send می‌تواند آن را کنار بگذارد و نشانی‌ای برایتان انتخاب کند
-f, --body-file <path>پرچم فایلی برای متن وجود ندارد. --html "$(cat body.html)" را بدهید، یا کل درخواست را در --data @email.json
-a, --attach <path>--attachments، آرایه‌ای JSON از فایل‌ها، هر کدام با یک filename و content به base64، یا با fileId فایلی که از پیش در فایل‌ها هست
--at <when>--scheduled-at <when>، یک لحظه به قالب ISO 8601 یا یک مدت مانند PT1H یا P2D. send تأخیرهای کوتاهی مانند 10m، 2h و 1d را هم می‌پذیرد
--undo <seconds>--cancellable-for-seconds <n>، از 0 تا 900
--translate <language>--translate '{"to":"de"}'، که from، includeOriginal و subject را هم می‌پذیرد
--template <id> --props <json>--template '{"id":"welcome","props":{"name":"Ada"}}'، که می‌تواند یک version را هم ثابت کند
--draft <id>--draft-id <id>
--thread <id>--thread-id <id>
--tag <key=value>--tags <key=value>، تکرارشده، یا یک شیء JSON

فقط emails send این‌ها را دارد: --tracking برای خاموش کردن ردیابی باز شدن یا کلیک در یک ارسال، --signature، --headers برای سرآیندهای سفارشی، --attachment-delivery برای انتخاب میان پیوست کردن فایل‌ها و پیوند دادن به آن‌ها، و --data برای کل بدنه به‌صورت JSON، درون‌خطی، از یک فایل با @path یا از stdin با -.

این دو به شکل متفاوتی پایان می‌یابند. send وقتی ایمیل با failed برگردد با کد 1 خارج می‌شود. emails send هر بار که API پاسخ داده باشد با کد 0 خارج می‌شود، پس status را در خروجی‌اش بررسی کنید.

همهٔ فرمان‌های emails

send، send-batch، translate، cancel و reschedule به emails:send نیاز دارند. list، get، list-events و get-tracking به emails:read نیاز دارند. شناسهٔ ایمیل msg_ است و پس از آن 24 نویسهٔ هگز، همان‌طور که یک ارسال آن را برمی‌گرداند.

فرمانچه می‌کند
openemail emails send --from <value> --to <a,b>یک ایمیل را همین حالا بفرستید، با --cancellable-for-seconds آن را برای یک پنجرهٔ لغو نگه دارید، یا با --scheduled-at زمان‌بندی‌اش کنید. متن --html، --text یا هر دو است، یک --template ذخیره‌شده، یا یک --draft-id ذخیره‌شده
openemail emails send-batch <emails>تا 100 ایمیل مستقل را در یک درخواست بفرستید، از یک آرایهٔ JSON در یک فایل، درون‌خطی، یا روی stdin با -. هر مورد شکلی مانند بدنهٔ emails send دارد و جداگانه موفق یا ناموفق می‌شود
openemail emails translate --to <value>پیش‌نمایش آنچه یک ارسال ترجمه‌شده تحویل می‌دهد، برای --subject، --html یا --text. چیزی ذخیره یا فرستاده نمی‌شود و یک کنش هوش مصنوعی مصرف می‌کند
openemail emails listیک صفحه از ایمیل‌های فرستاده‌شده، تازه‌ترین در ابتدا، محدودشده با --status، --from یا --broadcast-id
openemail emails get <id>یک ایمیل فرستاده‌شده با وضعیت، خطا و زمان تحویل هر گیرنده، و گزارش کامل ردیابی اگر ردیابی شده باشد
openemail emails list-events <id>ردپای رویدادهای یک ارسال، قدیمی‌ترین در ابتدا: پذیرفته شد، زمان‌بندی شد، فرستاده شد، تحویل شد، برگشت خورد، شکایت شد، باز شد، کلیک شد و بقیه
openemail emails get-tracking <id>گزارش تعامل یک ارسال: جمع‌هایش، یک درایه برای هر نسخهٔ ردیابی‌شده، و هر پیوند بازنویسی‌شده با کلیک‌هایش
openemail emails cancel <id>یک ایمیل در صف یا زمان‌بندی‌شده را پیش از رفتن متوقف کنید. از شما تأیید می‌خواهد
openemail emails reschedule <id> <scheduled-at>یک ایمیل در صف یا زمان‌بندی‌شده را به لحظه‌ای به قالب ISO 8601، یا مدتی مانند PT30M، از یک ثانیه تا 365 روز بعد جابه‌جا کنید

همهٔ فرمان‌های tracking

هر پنج به emails:read نیاز دارند. tracking get، list-opens و list-clicks هر یک از دو شناسهٔ یک پیام را می‌پذیرند: شناسهٔ msg_ که ارسالش برگرداند، یا شناسهٔ ردیابی tmsg_ که tracking list و محتوای وب‌هوک‌ها دارند.

فرمانچه می‌کند
openemail tracking listیک صفحه از پیام‌های ردیابی‌شده‌ای که در یک بازه فرستاده شده‌اند، تازه‌ترین در ابتدا، هر کدام با گزارش کاملش. --opened و --clicked آن را محدود می‌کنند و --no-opened آن‌هایی را نگه می‌دارد که کسی باز نکرده است. بازه 30 روز است مگر اینکه --days یا --minutes چیز دیگری بگوید
openemail tracking get-statsعددهای پشت یک پنل تعامل: پیام‌های ردیابی‌شده، بازشده و کلیک‌شده، نرخ باز شدن و کلیک، یک سری زمانی در بازه‌های --grain، و پیوندها، کلاینت‌های ایمیل و کشورهای برتر
openemail tracking get <id>گزارش تعامل یک پیام، همان سندی که emails get-tracking برمی‌گرداند
openemail tracking list-opens <id>تک‌تک باز شدن‌های پشت شمار باز شدن یک پیام، تازه‌ترین در ابتدا، هر کدام با برچسب human، proxy یا machine. --include-machine بازدیدهایی را که شمرده نشده‌اند هم اضافه می‌کند
openemail tracking list-clicks <id>تک‌تک کلیک‌ها روی پیوندهای یک پیام، تازه‌ترین در ابتدا، با url اصلی هر کدام. --include-machine پویشگرهای پیوند و تکرارهای ادغام‌شده را هم اضافه می‌کند

tracking list و get-stats همهٔ پیام‌های ردیابی‌شده‌ای را که صندوق پستی فرستاده پوشش می‌دهند، از جمله نامه‌هایی که در برنامهٔ وب نوشته شده و نامه‌هایی که ابزارهای MCP یا دستیار فرستاده‌اند، در حالی که emails list رکوردهای ارسالی را دارد که API ساخته است. در گزارشی که رکورد ارسال ندارد sendId برابر null است.

نمونه‌ها

از یک اسکریپت با کلید idempotency خودتان بفرستید. اجرای دوباره با همان --idempotency-key به‌جای فرستادن ایمیل دوم، ایمیل نخست را با replayed: true چاپ می‌کند.

فرستادن از یک اسکریپت
openemail emails send \  --from 'Acme Billing <[email protected]>' \  --to [email protected] \  --subject 'Your September invoice' \  --html '<p>The invoice is attached. Tell me if anything on it looks wrong.</p>' \  --attachments '[{"fileId":"file_6bb640f5b99e47deb758f1f5"}]' \  --tracking '{"opens":false}' \  --idempotency-key invoice:inv_2026_09_4192 \  --json | jq -r '.id + " " + .status'

بگذارید کسی ترجمه را پیش از رفتن بخواند. متن تأییدشده را به‌صورت --subject و --html ساده، بدون --translate بفرستید، وگرنه دوباره ترجمه می‌شود. html ترجمه‌شده از پیش متن اصلی شما را زیر خود دارد، مگر اینکه --no-include-original بدهید.

پیش‌نمایش یک ترجمه، سپس فرستادن آن
openemail emails translate --to de \  --subject 'Your September invoice' \  --html "$(cat invoice.html)" \  --json > preview.jsonjq -r .html preview.jsonopenemail emails send --from [email protected] --to [email protected] \  --subject "$(jq -r .subject preview.json)" \  --html "$(jq -r .html preview.json)"

یک دسته را از یک فایل بفرستید. فرمان هر بار که دسته پردازش شده باشد با کد 0 خارج می‌شود، حتی اگر برخی موارد ناموفق باشند، پس failed و status هر مورد را بخوانید. اجرای دوباره با همان کلید، مواردی را که رفته‌اند بازپخش می‌کند و فقط بقیه را می‌فرستد، به شرطی که آرایه ترتیبش را حفظ کند.

receipts.json
[  { "from": "[email protected]", "to": "[email protected]", "subject": "Receipt 4192", "text": "Thanks for your order." },  { "from": "[email protected]", "to": "[email protected]", "subject": "Receipt 4193", "text": "Thanks for your order." }]
فرستادن دسته
openemail emails send-batch receipts.json --idempotency-key receipts:2026-09-27 --json > result.jsonjq '{ sent, failed }' result.jsonjq -r '.items[] | select(.status == "error") | "\(.index) \(.error.code)"' result.json

یک ایمیل را زمان‌بندی کنید، جابه‌جا کنید و لغو کنید. --yes به تأییدی که cancel می‌خواهد پاسخ می‌دهد، کاری که اسکریپت نمی‌تواند.

زمان‌بندی، جابه‌جایی و لغو
ID=$(openemail send --from [email protected] --to [email protected] --subject "Standup notes" \  --body-file notes.md --at 2026-10-01T09:00:00Z --json | jq -r .id)openemail emails reschedule "$ID" 2026-10-01T13:00:00Zopenemail emails get "$ID" --json | jq -r '.status + " " + .scheduledAt'openemail emails cancel "$ID" --yes

ارسال‌های ناموفق را پیدا کنید و ببینید چه بر سر یکی از آن‌ها آمده است. وقتی خروجی بدون --json به لوله داده شود، --all در هر سطر یک شیء JSON چاپ می‌کند.

پیدا کردن ارسال‌های ناموفق
openemail emails list --status failed,partial --from [email protected] --all | jq -r .idopenemail emails get msg_3f9a1c07d2b84e6a9c5b1f20openemail emails list-events msg_3f9a1c07d2b84e6a9c5b1f20 --all --json | jq -r '.items[] | .createdAt + " " + .type'

یک هفته تعامل را در روزهایی بخوانید که در نیمه‌شب UTC+2 جدا می‌شوند، آنچه را کسی باز نکرده فهرست کنید و کلیک‌های هر پیوند یک پیام را بشمارید.

یک هفته باز شدن و کلیک
openemail tracking get-stats --days 7 --offset-minutes 120 --json | jq '{ tracked, openRate, clickRate }'openemail tracking list --no-opened --days 7 --all | jq -r .subjectopenemail tracking list-clicks msg_3f9a1c07d2b84e6a9c5b1f20 --all | jq -r .url | sort | uniq -c

دامنه‌های مجوز، کدها و تأییدها

  • ورود با مرورگر دامنه‌های مجوز را در صفحهٔ تأیید می‌خواهد، و openemail login --scopes emails:send,emails:read هر دو را از پیش انتخاب می‌کند. فرمانی که دامنهٔ مجوزش را ندارد با کد خروج 4 و insufficient_scope متوقف می‌شود و نام دامنهٔ مجوز را می‌آورد.
  • send --attach با بیش از 5 MB فایل، نخست آن‌ها را در فایل‌ها بارگذاری می‌کند، که به files:write هم نیاز دارد.
  • هیچ‌کدام از این فرمان‌ها کد تأیید هویت نمی‌خواهد، پس ورود با مرورگر آن‌ها را همان‌طور اجرا می‌کند که یک کلید API.
  • emails cancel پیش از لغو می‌پرسد و --yes به جای شما پاسخ می‌دهد. بدون نظارت و بدون --yes، با Refusing to run unattended. Pass --yes to confirm. و کد خروج 2 متوقف می‌شود.
  • emails send، send-batch و reschedule هرگز نمی‌پرسند. send خلاصه‌ای نشان می‌دهد و فقط در ترمینال می‌پرسد، و --yes از آن هم می‌گذرد.
  • --dry-run درخواستی را که فرمان می‌فرستاد چاپ می‌کند، چیزی نمی‌فرستد و با کد 0 خارج می‌شود. روی emails translate هیچ کنش هوش مصنوعی خرج نمی‌کند و روی emails cancel چیزی نمی‌پرسد.

صفحه‌های نتیجه

emails list، emails list-events، tracking list، list-opens و list-clicks یک صفحه می‌خوانند. --limit اندازهٔ آن را تعیین می‌کند، از 1 تا 100 با پیش‌فرض 25 برای دو فهرست emails، و از 1 تا 200 با پیش‌فرض 50 برای سه فهرست tracking. --cursor از نشانگری که یک صفحه چاپ کرده ادامه می‌دهد.

  • --all همهٔ صفحه‌ها را می‌خواند و موارد را جریانی می‌فرستد: در ترمینال یک جدول، و وقتی به لوله داده شود یا با --ndjson در هر سطر یک شیء JSON.
  • --max <n> پس از همان تعداد مورد می‌ایستد و --all را هم در بر دارد.
  • --json یک سند { items, hasMore, nextCursor } چاپ می‌کند، با --all هم.
  • صفحه‌بندی با نشانگر است نه با آفست، پس نامه‌ای که هنگام ورق زدن شما فرستاده شود هرگز ردیفی را جابه‌جا یا تکرار نمی‌کند.

دانستنی‌ها

  • هر اجرا کلید idempotency خودش را می‌سازد که تلاش‌های دوباره در همان اجرا را پوشش می‌دهد. دو بار اجرای یک ارسال دو بار می‌فرستد، مگر اینکه هر دو اجرا همان --idempotency-key را بدهند. همان کلید با بدنه‌ای دیگر با idempotency_key_reuse و کد خروج 7 رد می‌شود.
  • فقط نامهٔ queued و scheduled را می‌توان لغو یا جابه‌جا کرد. ارسال فوری بدون پنجرهٔ لغو درون همان درخواست بیرون می‌رود، پس وقتی شناسه‌اش به دستتان برسد معمولاً دیر شده است و فراخوانی با email_not_cancellable و کد خروج 6 پایان می‌یابد.
  • ایمیل لغوشده لغوشده می‌ماند. زمان‌بندی دوباره فقط زمان را تغییر می‌دهد، که برای یک مدت از لحظهٔ دریافت درخواست به دست سرور شمرده می‌شود، پس برای تغییر متن، لغو کنید و دوباره بفرستید.
  • ترجمه‌ای که نتوان تولیدش کرد کل ارسال را رد می‌کند و هیچ چیز ترجمه‌نشده بیرون نمی‌رود. یک دستهٔ ترجمه‌شده حداکثر 10 پیام دارای translate دارد.
  • سهمیهٔ ارسالِ تمام‌شده ارسال را با send_quota_exceeded تا اول ماه متوقف می‌کند، و سهمیهٔ تمام‌شدهٔ هوش مصنوعی ترجمه را با ai_quota_exceeded تا نیمه‌شب UTC، هر دو با کد خروج 8.
  • نامه‌ای که با کلید oe_test_ فرستاده شود هرگز تحویل داده نمی‌شود. وضعیتش sent است، با transport برابر test، و هرگز ردیابی نمی‌شود.
  • emails get-tracking و tracking get برای پیامی که نه پیکسل داشت و نه پیوند بازنویسی‌شده، 404 با کد خروج 5 پاسخ می‌دهند، چون ردیابی‌نشده با بازنشده یکی نیست. ردیابی از تنظیمی پیروی می‌کند که پیام با آن فرستاده شده، پس روشن کردنش در آینده به نامه‌های پیشین نمی‌رسد.
  • هر شمارشی کف است. خواننده‌ای که کلاینت ایمیلش تصاویر را مسدود می‌کند هرگز باز شدن به حساب نمی‌آید، و کلیک شاهد قوی‌تری از خواندن است تا باز شدن.
  • list-opens و list-clicks برای شناسهٔ msg_ که چیزی از آن ردیابی نشده 404 پاسخ می‌دهند، اما شناسهٔ tmsg_ را همان‌طور که هست می‌پذیرند، پس شناسهٔ ناشناخته با فهرستی خالی برمی‌گردد.
  • کلیدی که به برخی نشانی‌ها محدود است فقط نامه‌هایی را می‌بیند که از همان نشانی‌ها فرستاده شده‌اند، و کلیدی که یک دامنهٔ کامل را دارد همهٔ نشانی‌های آن را پوشش می‌دهد.

همهٔ پرچم‌ها

این صفحه مهم‌ترین پرچم‌ها را نام می‌برد. openemail <command> --help هر آرگومان و پرچمی را که فرمان می‌گیرد فهرست می‌کند، با نوعش، دامنهٔ مجوزی که لازم دارد، متد و مسیرش، آنچه برمی‌گرداند و یادداشت‌های مرجع API. برای همان راهنما به‌صورت یک سند JSON، --json را اضافه کنید.

ترمینال
openemail emails --helpopenemail emails send --helpopenemail tracking list-opens --help --json

صندوق ورودی شما،
با شرایط خودتان.

زیرساخت ایمیل برای کسب‌وکارها، هوش مصنوعی، عامل‌ها و ایمیل شخصی. ساخته‌شده برای مقیاس، حریم خصوصی و کنترل. هر چه ایمیل باید از روز نخست می‌داشت.

OpenEmail

زیرساخت ایمیل برای کسب‌وکارها، هوش مصنوعی، عامل‌ها و ایمیل شخصی. ساخته‌شده برای مقیاس، حریم خصوصی و کنترل. هر چه ایمیل باید از روز نخست می‌داشت.

© 2026 OpenEmail. همه حقوق محفوظ است.