20 KiB
گزارش جامع: اعتبارسنجی گزارشها و راهکار کرال موتور STT بله
تاریخ: ۱۵ مهر ۱۴۰۵
موضوع: افزودن متن تولیدشده توسط قابلیت «تبدیل ویس به متن» پیامرسان بله بهعنوان یک کاندید در خطلوله چندمدله STT بات تدارکات
ورودیها: سه سند ارائهشده (تحلیل جامع، پلیبوک اجرایی، تحلیل مقایسهای) + راستیآزمایی مستقل وب
محدودیت:integration_reportشماره ۱ و ۲ در دسترس من نبود و فقط از روی نقلقولهای همین اسناد قضاوت شدهاند. دستورهای کشف (بخش ۴) در محیط من اجرا نشدهاند، چون شبکه sandbox بسته بود.
۱. خلاصه مدیریتی
- Bot API رسمی بله STT ندارد. همه اسناد در این مورد درست میگویند.
- تناقض اصلی (مهندسی معکوس «غیرعملی است» در برابر «ساده است») هیچکدام کاملاً درست نیست. مسیر شدنی است، ولی «افزودن یک متد» نیست و نیاز به یک فاز کشف دارد.
- دو فرض اثباتنشده کل مسیر را تحت تأثیر قرار میدهد:
- دکمه «تبدیل به متن» روی وب بله وجود دارد (هر سه سند فرض کردهاند، هیچ منبعی تأیید نکرده).
- پکیج
aiobale-pyنسخه 0.3.9 فعال است (پیدا نشد؛ به بخش ۲ مراجعه کنید).
- کشف جدید: پکیج
bale-sdkبا ۶۰۷ RPC تایپشده و پروتوهای بازیابیشده. احتمال وجود RPC ترنسکریپشن در آن بالاست. ولی مجوز آن اختصاصی است. - بزرگترین صرفهجویی: آزمون دقت را قبل از ساخت و بهصورت دستی روی ۳۰ ویس واقعی انجام دهید. اگر بله از خطلوله فعلی بهتر نبود، پروژه لازم نیست.
- ریسک حقوقی/ToS (استفاده خودکار از حساب کاربری) تصمیم مدیریتی است و باید قبل از استقرار روشن شود.
۲. اعتبارسنجی گزارشها
۲.۱ جدول ادعاها
| ادعا | نتیجه | توضیح |
|---|---|---|
| Bot API رسمی STT ندارد | ✅ تأیید | پروبها همگی ۴۰۴ دادهاند و تایپهای SDKها برای Voice فقط شناسه فایل و مدتزمان دارند. تذکر: ۴۰۴ برای نامهای حدسی چیزی درباره فیلد مخفی در payload نمیگوید؛ تست T1 (ویس به یک بات تستی و خواندن JSON کامل) هنوز لازم است (۳۰ دقیقه). |
| بله قابلیت تبدیل ویس به متن دارد | ✅ با شرط | نسخه جدید بله این قابلیت را برای اندروید و iOS منتشر کرده. وجود دکمه در وب تأییدنشده است و ریسک اصلی مسیر Playwright همین است. |
| مهندسی معکوس «غیرعملی» است (گزارش ۲) | ⚠️ بدبینانه | کلاینتهای متنباز مهندسیمعکوسشده وجود دارند. اما استدلال «Protobuf خودتوصیف است» نادرست است: wire format بدون .proto فقط تا حدی (شماره فیلد و نوع خام، بدون نام و معنا) دیکود میشود. |
| مهندسی معکوس «در حد افزودن یک متد» است (پلیبوک) | ⚠️ خوشبینانه | کشف RPC، نگاشت فیلدها و پایداری نشست کار واقعی است. تخمین «نیمروز» برای T2 ریسکی است. |
aiobale-py v0.3.9 فعال است و نام aiobale را پکیج خالی گرفته |
❌ تأییدنشده / احتمالاً غلط | aiobale-py را پیدا نکردم. aiobale یک کتابخانه واقعی است (MIT، مستندات docs.aiobale.ir، نسخههای 0.1.x). فورکهایی مثل Autobale میگویند نسخه اصلی نگهداری نمیشود و باگ دارد. قبل از وابستگی به هر نام، pip index versions را اجرا کنید. |
bale-sdk (کشف جدید) |
🔎 مهم | از کلاینت وب بله مهندسی معکوس شده؛ ۶۰۷ RPC در ۵۲ سرویس، پروتوهای بازیابیشده، احراز با JWT یا OTP؛ نسخه 0.1.1 (ژوئن ۲۰۲۶). مجوز اختصاصی و «همه حقوق محفوظ». |
| تأخیر «زیر ۱ ثانیه» | ❌ رد | همه موافقند. اعداد ۱–۴ ثانیه (R2) و ۴–۸ ثانیه (Playwright) هم اندازهگیری نشدهاند؛ فقط T5 عدد واقعی میدهد. |
| AI Chat بله ویس را «پیاده» میکند (R3) | ⚠️ تأییدنشده و نامطلوب | حتی اگر درست باشد، خروجی «متن + تفسیر مدل» است و برای consensus مناسب نیست. با کنار گذاشتن موافقم. |
| RAM ۳۵۰–۵۰۰ مگابایت برای Playwright | ✅ معقول | برای بات تککاربره قابلتحمل است. |
| Playwright در ۱–۲ روز | ⚠️ خوشبینانه | وابسته به وجود دکمه وب، چالشهای ورود و پایداری سلکتورها. |
| ساختار Gate / State-machine پلیبوک | ✅ قوی | بهترین بخش اسناد. ایراد: دروازه دقت (T7) بعد از ساخت آمده، در حالی که دستی و قبل از ساخت شدنی است. |
| ریسک بن، ToS و حریم خصوصی | ✅ درست و حیاتی | فقط پلیبوک به آن پرداخته است. |
| ترجیح WebSocket به POST gRPC (پلیبوک) | ✅ منطقی | کلاینت رسمی بله POST gRPC را عمدتاً برای چند متد احراز هویت استفاده میکند؛ استفاده زیاد از آن غیرعادی به نظر میرسد. |
| «Playwright اول» (سند مقایسهای) در برابر «R2 اول» (پلیبوک) | ⚠️ هر دو مشروط | بدون نتیجه کشف روز اول قابل تصمیم نیست. |
۲.۲ ایرادهای کد adapter در سند اول
- کلید پیشفرض ضعیف (
bale_secure_token) و مقایسه کلید با!=بهجای مقایسه ثابتزمان. - بلعیدن همه استثناها بدون لاگ.
- بازگرداندن ۲۰۰ با متن خالی: ممکن است بات آن را یک کاندید معتبر (خالی) در consensus بشمارد. باید در
bot/app/stt.pyبررسی شود که پاسخ ۵xx و متن خالی چطور مدیریت میشوند. توصیه: در خطا ۵۰۳ برگردد. - نبود قفل ترتیبی، سقف روزانه و تأخیر تصادفی در خود adapter.
۲.۳ نکات فنی اصلاحشده
- فریم gRPC-Web پیشوند ۵ بایتی دارد (۱ بایت فلگ + ۴ بایت طول). این برای POST gRPC-Web درست است؛ اینکه فریمهای WebSocket بله هم همان قالب را دارند فرض اثباتنشدهای است و باید در T2 دیده شود.
- هاستها و نام ماژولهایی مثل
maviz-ws.bale.aiوSpeechTranscriptاز تحلیل باندل آمدهاند و در وب ایندکس نشدهاند. باید با چشم در کپچر تأیید شوند.
۳. راهکارها
| راهکار | توضیح | رم | خلوص متن | ریسک | حکم |
|---|---|---|---|---|---|
| A. مسیر رسمی | درخواست API یا همکاری از بله | — | — | — | هزینه صفر؛ قبل از هر کار غیررسمی یک ایمیل بزنید |
| B. RPC مستقیم | کلاینت کاربری روی WebSocket با bale-sdk یا aiobale + RPC ترنسکریپت |
≈ ۲۰ MB | خالص | متوسط (تغییر پروتکل، بن) | بهترین نتیجه فنی، مشروط به کشف RPC |
| C. Playwright | Chromium headless روی web.bale.ai با پروفایل پایدار |
۳۵۰–۵۰۰ MB | خالص | کم–متوسط | مقاوم، فقط اگر دکمه وب موجود باشد |
| D. AI Chat | ویس به چت هوش مصنوعی بله و استخراج از پاسخ | ≈ ۲۰ MB | ❌ متن + تفسیر | بالا | کنار گذاشته شود |
| E. سرویس ثالث | پروکسیهای STT با ادعای بله | — | نامشخص | حریم خصوصی/پایداری | کنار گذاشته شود |
| F. اندروید امولاتور | اپ بله + uiautomator | زیاد | خالص | بالا (شکننده) | آخرین چاره اگر B و C ممکن نشد |
۴. مسیر دقیق اجرا
گام ۰: آزمون دقت دستی (نیمروز، بدون کد)
۳۰ ویس واقعی تدارکاتی (با رضایت فرستندگان؛ صداها را بلندمدت نگه ندارید) را در اپ بله دستی به متن تبدیل کنید و سه حالت را مقایسه کنید:
- خروجی فعلی بات (whisper/سایرین + consensus)
- فقط متن بله
- consensus با اضافهشدن بله
سه معیار: WER متن، دقت استخراج اقلام (نام کالا، برند، تعداد، واحد) و تعداد موارد سخت لهجهای که با بله درست شدهاند.
معیار پیشنهادی: کاهش نسبی خطای استخراج حدود ۱۵٪ یا بیشتر، یا حل حداقل ۲ مورد سخت. در غیر این صورت STOP.
گام ۱: کشف سریع (حدود ۳۰ دقیقه)
python -m venv .v && . .v/bin/activate
pip index versions aiobale-py # وجود یا عدم وجود را بررسی کنید
pip download bale-sdk --no-deps --no-binary :all: && tar xzf bale_sdk-*.tar.gz
grep -rniE "transcri|speech|asr|stt" bale_sdk-*/proto bale_sdk-*/docs | head -50
همچنین در پایتون from bale import ALL_RPCS را با همان کلیدواژهها فیلتر کنید.
همزمان T1: یک بات تستی مستقل بسازید، یک ویس بفرستید و JSON کامل آپدیت را بخوانید. اگر فیلد ترنسکریپشن وجود داشت، پروژه کرالر لازم نیست.
گام ۲: وب و کپچر (نیمروز تا یک روز)
- با یک حساب اختصاصی شرکت روی
web.bale.aiوارد شوید و بررسی کنید دکمه «تبدیل به متن» روی ویس هست یا نه (روی ویس دریافتی و ارسالی). - DevTools تب Network را با Preserve log و فیلتر WS و Fetch/XHR ضبط کنید و هنگام کلیک روی دکمه ذخیره کنید:
- URL کامل و ترابری (unary یا WS)
- هدر احراز
req.binوresp.bin- زمان پاسخ (همان تأخیر واقعی ASR)
- ۵ تا ۱۰ ویس متنوع (کوتاه، بلند، لهجهدار) را تکرار کنید و در
findings.mdخلاصه کنید. - دیکود آفلاین: پیشوند ۵ بایتی را بردارید، سپس
protoc --decode_rawیاprotoscope.
گام ۳: انتخاب مسیر
| وضعیت | مسیر |
|---|---|
RPC در bale-sdk یا کپچر پیدا شد |
B |
| RPC پیدا نشد ولی دکمه وب هست | C |
| هیچکدام | F یا توقف |
| ترنسکرایب نیاز به امضا یا اثر انگشت مرورگر دارد | C |
الگوی پیشنهادی برای B: بات خودتان با sendVoice(file_id) ویس را برای حساب کرالر بفرستد (کرالر یکبار بات را /start کرده). اینطور نیازی به دانلود و آپلود مجدد نیست و message_id بومی در اختیار کرالر است. پس از دریافت متن، پیام حذف شود. اگر RPC به message_id نیاز نداشت، مستقیم فایل یا بایت داده شود.
مجوز: aiobale مجوز MIT دارد ولی نگهداری نمیشود (فورکها: Autobale و BaleClient). bale-sdk مجوز اختصاصی دارد؛ برای استفاده تجاری از نویسنده اجازه بگیرید.
گام ۴: ساخت adapter سختشده
قرارداد OpenAI-compatible (همان POST /v1/audio/transcriptions که بات انتظار دارد) و موتور قابلسوییچ با BALE_STT_ENGINE=grpc|playwright. پیشنهاد کد:
import os, secrets, asyncio, logging
from fastapi import FastAPI, File, Form, Header, HTTPException, UploadFile
log = logging.getLogger("bale-stt")
app = FastAPI()
KEY = os.environ["BALE_STT_INTERNAL_KEY"] # بدون مقدار پیشفرض
DAILY_CAP = int(os.environ.get("BALE_STT_DAILY_CAP", "100"))
lock = asyncio.Lock() # اجرای ترتیبی
count_today = 0 # در عمل با ریست روزانه
@app.get("/healthz")
def healthz():
return {"status": "ok"}
@app.post("/v1/audio/transcriptions")
async def transcribe(file: UploadFile = File(...), model: str = Form("bale-stt"),
language: str = Form("fa"), authorization: str = Header("")):
if not secrets.compare_digest(authorization, f"Bearer {KEY}"):
raise HTTPException(401)
if count_today >= DAILY_CAP:
raise HTTPException(429)
async with lock:
try:
text = await run_engine(await file.read()) # + تأخیر تصادفی ۱ تا ۳ ثانیه
except Exception:
log.exception("bale stt failed")
raise HTTPException(503) # تا بات فقط همین کاندید را حذف کند
if not text:
raise HTTPException(503)
return {"text": text}
اتصال به بات (بدون تغییر کد):
PROCUREMENT_BOT_STT_PROVIDER_3_NAME=bale
PROCUREMENT_BOT_STT_PROVIDER_3_BASE_URL=http://bale-stt:8080/v1
PROCUREMENT_BOT_STT_PROVIDER_3_API_KEY=<INTERNAL_KEY>
PROCUREMENT_BOT_STT_PROVIDER_3_MODEL=bale-stt
PROCUREMENT_BOT_STT_PROVIDER_3_LANGUAGE=fa
پرووایدر فقط وقتی فعال میشود که هم
BASE_URLو همAPI_KEYپر باشند.
گام ۵: عملیات و ایمنی
- فقط شماره اختصاصی شرکت؛ هرگز شماره شخصی.
session_fileیا پروفایل مرورگر روی ولوم داکر و هرگز در گیت.- OTP تنها گام انسانی است. در ابطال نشست: هشدار به ادمین و هدایت ترافیک به سایر پرووایدرها.
- اجرای ترتیبی، فاصله تصادفی ۱ تا ۳ ثانیه، سقف روزانه، و ترجیح WebSocket به POST gRPC.
- حذف فوری پیام اسکرچ پس از استخراج و عدم نگهداری فایل صوتی روی دیسک.
- پایش: نرخ موفقیت، p50 و p95 تأخیر، انواع خطا، وضعیت نشست. هشدار اگر نرخ خطا در ۳۰ دقیقه بیش از ۲۰٪ شد.
- Rollback: خالی کردن
STT_PROVIDER_3_*در env بات و توقف کانتینر. بات فوراً به وضعیت قبل برمیگردد. - سکرتهایی که در
docker-compose.ymlکامیت شدهاند (توکن بات، کلید DeepSeek) باید rotate شوند وDRAFT_TOKEN_SECRETپیشفرض ضعیف را عوض کنید. - روی برنچهای دیگران (
prod-v7و غیره) دخالت نکنید و بدون تأیید مالک چیزی پوش نشود.
گام ۶: اندازهگیری و سواک
- T5: ۵۰ تا ۱۰۰ ویس ترتیبی با فاصله انسانی؛ پذیرش پیشنهادی: موفقیت ≥ ۹۵٪ و p95 ≤ ۸ ثانیه.
- سواک یکهفتهای با حجم کم (حدود ۱۰۰ ترنسکرایب در روز): ثبت تعداد ورود مجدد، چالشهای امنیتی و عمر واقعی توکن.
۵. دروازههای تصمیم (خلاصه)
| دروازه | شرط عبور | در صورت شکست |
|---|---|---|
| G0 دقت دستی | بهبود ≈ ۱۵٪ یا ۲ مورد سخت | STOP |
| G1 (T1) | فیلد ترنسکریپشن نبود | اگر بود: پایان، مستقیم وصل شود |
| G2 کشف | RPC یا دکمه وب پیدا شد | F یا توقف |
| G3 پروتوتایپ | درخواست ساخته و پاسخ خوانده شد | سوییچ به C |
| G4 نرخ و پایداری | ≥ ۹۵٪ موفقیت، p95 ≤ ۸ ثانیه | کاهش نرخ و backoff؛ در صورت بن: توقف |
| G6 ToS | تصمیم مکتوب مدیریت | STOP یا حجم بسیار محدود |
| G7 سواک | نشست سالم یک هفته | rollback و بازگشت به G4 |
۶. زمانبندی واقعبینانه
| مرحله | زمان |
|---|---|
| گام ۰ و ۱ (دقت دستی + کشف سریع) | نیمروز |
| گام ۲ (وب و کپچر) | ۱ روز |
| ساخت B یا C | ۲ تا ۴ روز |
| T5 و سواک | ۱ هفته |
۷. رجیستر ریسک
| ریسک | احتمال | اثر | مقابله |
|---|---|---|---|
| بن یا rate-limit حساب | متوسط | توقف مسیر | حجم کم، WS-first، سقف روزانه، حساب اختصاصی قابلتعویض |
| تغییر پروتکل یا UI بله | متوسط | قطع سرویس | هشدار خطا، فالبک، سوییچ موتور با env، rollback با env |
| انقضای نشست و نیاز به OTP | بالا (دورهای) | توقف موقت | ولوم نشست + هشدار + runbook ورود انسانی |
| دکمه وب وجود ندارد | نامعلوم | ناممکنشدن C | بررسی در گام ۲ قبل از ساخت |
| دقت ناکافی نسبت به هزینه | نامعلوم | هزینه بیفایده | G0 قبل از ساخت |
| ToS / مسائل حقوقی | نامعلوم | توقف اجباری | تصمیم مکتوب مدیریت (G6)؛ ایمیل به بله (A) |
مجوز اختصاصی bale-sdk |
بالا | ممنوعیت استفاده | اجازه از نویسنده یا استفاده از aiobale (MIT) |
| حریم خصوصی صدا | کم | اعتباری | حذف فوری پیامها، عدم نگهداری فایل |
| وابستگی به یک فرد نگهدارنده | متوسط | رکود | مستندسازی و مالک رسمی |
۸. دروازههای انسانی
- OTP ورود حساب (بار اول و هر انقضا).
- تصمیم ToS / حقوقی.
- جمعآوری نمونه ویس واقعی با رضایت.
- تأیید نهایی استقرار و مرج توسط مهندس ارشد.
۹. توصیه نهایی
- همین هفته: گام ۰ (دقت دستی) + ایمیل به بله + گام ۱ (کشف سریع و T1).
- اگر دقت توجیه داشت: گام ۲ و انتخاب B یا C بر اساس شواهد.
- معماری: adapter با قرارداد OpenAI و موتور قابلسوییچ؛ بات دستنخورده میماند.
- تصمیم مدیریتی درباره ToS قبل از استقرار.
- اگر هر کدام از G0 یا G6 شکست خورد، توقف و ادامه با پرووایدرهای فعلی.
منابع
- aiobale (PyPI): https://pypi.org/project/aiobale
- bale-sdk (PyPI): https://pypi.org/project/bale-sdk/
- Autobale (فورک aiobale): https://pypi.org/project/autobale/
- خبر انتشار نسخه بله با قابلیت تبدیل پیام صوتی به متن (خبرگزاری آنا): https://ana.ir/fa/news/994908
- مستندات رسمی بات بله: https://docs.bale.ai