یک دستیار کدنویسی مبتنی بر هوش مصنوعی در صف سرور رایگان، پس از ناپدید شدن قانون «تجمد مهاجرتها» (freeze migrations) در حین فشردهسازی خودکار بافتار (context compaction)، یک فایل مهاجرت طرحواره (schema-migration) نوشت. این حادثه نشان میدهد که تکیه بر دستورالعملهای مبتنی بر پرامپت برای اعمال امنیت میتواند زمانی که جلسات طولانی چت خلاصه میشوند، نتیجه معکوس داشته باشد.
چه اتفاقی افتاد
یک عامل کدنویسی مشترک با یک پرامپت سیستمی اجرا میشد که حاوی یک قانون واحد بود: فایلهای مهاجرت را ایجاد یا اصلاح نکن. این قانون باعث میشد مهاجرتهای طرحواره در شاخه انتشار (release branch) ثابت بمانند، در حالی که توسعهدهندگان از عامل برای ویرایشهای روتین استفاده میکردند.
در طول یک جلسه طولانی، گفتگو از محدودیت توکن مدل فراتر رفت. سرور دستور context compaction را فراخوانی کرد و تاریخچه کامل چت را با یک خلاصه کوتاه جایگزین کرد تا در محدوده بودجه توکن باقی بماند. خلاصه، اشاره به مسیرهای فایل را حفظ کرد اما محدودیت منفی («در migrations/** ننویس») را حذف کرد. وقتی مدل پاسخ بعدی خود را تولید کرد، قانون تجمد دیگر در حافظه کاری آن نبود.
سپس عامل یک اصلاح SQL برای بهبود سرعت پرسوجو پیشنهاد داد. ابزار همراه، این تغییر را به عنوان یک فایل مهاجرت روی دیسک ذخیره کرد. تستهای واحد (Unit tests) با موفقیت پاس شدند زیرا آنها هرگز مهاجرتهای SQL خام را اجرا نمیکنند، و این تغییر تنها بعداً در یک diff بررسی کد (code-review) مشاهده شد.
چرا این موضوع اهمیت دارد
- حفاظهای امنیتی ناپدید شدند: سیاستهای سطح پرامپت ناپایدار هستند. وقتی بافتار مدل فشرده میشود، هر بند «انجام نده» میتواند از بین برود و سیستم را برای انجام اقدامات ممنوعه آزاد بگذارد.
- تستهای واحد کافی نیستند: تستهایی که اسکریپتهای مهاجرت را اجرا نمیکنند، میتوانند احساس امنیت کاذبی ایجاد کنند. این تغییر از زیر دستها در رفت چون مجموعه تستها هرگز SQL جدید را اجرا نکردند.
- تأخیر در بررسی انسانی: زمانی که یک بازبین (reviewer) تغییرات (diff) را دید، فایل مهاجرت قبلاً ثبت (commit) شده بود و نیاز به بازگشت (rollback) یا پاکسازی اضافی داشت.
این خطا باعث قطعی نشد، اما کار اضافی برای بازگرداندن یک مهاجرت غیرضروری تحمیل کرد و خطر لغزش مشابهی که دیتابیسهای زنده را تحت تأثیر قرار دهد، افزایش داد.
چگونه حفاظ امنیتی شکست خورد
- قانون فقط در پرامپت – قانون تجمد به صورت متن ساده در پرامپت سیستمی وجود داشت.
- جلسه طولانی – چت از پنجره بافتار (context window) مدل فراتر رفت.
- فشردهسازی – سرور متن کامل را با یک خلاصه پر از اسم (noun) جایگزین کرد.
- از دست رفتن محدودیت منفی – خلاصه، دستور «انجام نده» را حذف کرد و قانون را از بین برد.
- خروجی مدل – بدون وجود قانون، مدل پاسخی تولید کرد که منجر به ایجاد مهاجرت شد.
خلاصهسازها تمایل دارند اسمها (مسیر فایلها، نام توابع) را نگه دارند و نفیها (negations) را حذف کنند، به همین دلیل است که قانون بیصدا ناپدید شد.
راه حل: انتقال حفاظهای امنیتی به مسیر نوشتن
به جای گنجاندن ممنوعیتها در پرامپت، آنها را در جایی که کد با دیسک تماس پیدا میکند، اعمال کنید.
- یک فایل سیاست ایجاد کنید (مثلاً
agent_policy.txt) که مسیرهای لیست سیاه مانندschema/**یاmigrations/**را فهرست میکند. - یک اسکریپت پیشاعمال (pre-apply) اضافه کنید که فایل سیاست را بخواند و هر diff را قبل از اجرای ابزار اعمال، اسکن کند.
- در صورت بروز خطا، دسترسی را ببندید (Fail closed)؛ اگر فایل سیاست مفقود، خالی یا اگر یک diff به مسیر ممنوعه دسترسی داشت، عملیات متوقف شود.
- از مدل نخواهید لیست سیاه را تأیید کند؛ تأیید کردن تنها یک سیگنال است، نه ابزار اعمال اجباری.
حفاظهای فقط پرامپت در مقابل حفاظهای مبتنی بر دیسک
| جنبه | تجمد فقط در پرامپت | دروازه مبتنی بر دیسک |
|---|---|---|
| ریسک فشردهسازی | قانون میتواند ناپدید شود | فایل سیاست دستنخورده باقی میماند |
| پوشش تست واحد | ممکن است نوشتنهای ممنوعه را از دست بدهد | بررسی مسیر، نوشتن را بدون توجه به تستها مسدود میکند |
| زمان بررسی انسانی | ممکن است آسیب قبلاً ثبت شده باشد | نوشتن هرگز شروع نمیشود، بازبین تغییری نمیبیند |
| تلاش برای پیادهسازی | حداقلی (فقط یک خط در پرامپت) | اسکریپت کوچک + فایل سیاست |
نقطه مقابل
آنچه در مرحله بعد باید مراقب بود
نتیجهگیری
اگر به قانونی نیاز دارید که هرگز نباید نادیده گرفته شود — مانند «عدم انجام مهاجرت در زمان تجمد» — آن را روی دیسک ذخیره کنید و در نقطه نوشتن اعمال کنید. متن پرامپت به تنهایی نمیتواند دوام قانون را پس از فشرده شدن بافتار مدل تضمین کند.
