- مفاتيح توقيع JWT — أزواج مفاتيح غير متماثلة ES256 (مع علامة
kid) مُخزَّنة فيcore."signingKey"، تُستخدم لتوقيع والتحقق من رموز الوصول / التحديث. - مفتاح التشفير أثناء السكون (At-rest encryption key) —
ENCRYPTION_KEY، يُستخدم لتشفير رموز OAuth، ومتغيرات التطبيق، ومفاتيح التوقيع الخاصة، وقيم الإعدادات الحساسة، وأسرار TOTP داخل غلافenc:v2:.
APP_SECRET سراً قديماً مُحتفَظاً به لأغراض التوافق مع الإصدارات السابقة: عندما لا يكون ENCRYPTION_KEY مضبوطاً، فإنه يعمل كحل احتياطي لمفتاح التشفير أثناء السكون / ملفات تعريف الارتباط للجلسة، ولا يزال يتحقق من رموز الوصول HS256 الموجودة مسبقاً. سيتم إهماله (إيقاف دعمه).
مفاتيح توقيع JWT
يحمل كل مفتاح قيمةpublicKey (يُحتفَظ بها إلى أجل غير مسمى حتى يمكنها التحقق من الرموز المصدرة مسبقاً)، وprivateKey مُشفَّراً (يُستخدم فقط أثناء كون المفتاح حالياً)، وراية isCurrent (صف واحد فقط في كل وقت)، وحقل revokedAt اختياري.
تدوير المفتاح الحالي
اضبطSIGNING_KEY_ROTATION_DAYS للتفعيل: عندها تصدر مهمة cron يومية مفتاحًا حاليًا جديدًا بمجرد أن يصبح المفتاح القائم أقدم من تلك العتبة. لا يتم إبطال المفاتيح السابقة، لذلك تستمر الرموز الموقعة تحتها في التحقق. اترك المتغير غير معيّن لتعطيل التدوير التلقائي.
ميزة التدوير التلقائي متوفّرة ابتداءً من الإصدار v2.6+.
إبطال مفتاح (في حالات التسريب / الطوارئ فقط)
Settings → Admin Panel → Signing keys → Revoke على صف غير حالي. تعمل على مسح المادة الخاصة المشفرة، وتعيينrevokedAt، ورفض كل رمز حالي موقَّع تحت هذا الـ kid.
تدوير ENCRYPTION_KEY
أمر
secret-encryption:rotate الموضَّح أدناه متوفر ابتداءً من الإصدار v2.6+.enc:v2:\<keyId>:\<payload>، حيث إن \<keyId> هو بادئة مكوَّنة من 8 أرقام ست عشرية مشتقة من المفتاح الخام. تتم عملية التدوير (الاستبدال) أثناء العمل، وقابلة للاستئناف.
-
إنشاء مفتاح جديد:
openssl rand -base64 32. -
ضَبْط المفتاحين معاً جنباً إلى جنب في ملف
.env، ثم إعادة تشغيل الخدمة:تستخدم عمليات الكتابة الجديدة المفتاح الجديد، بينما لا تزال الصفوف الحالية تُفك تشفيرها عبر المفتاح الاحتياطي (fallback). -
إعادة تشفير الصفوف الحالية:
يتناول الأمر ستة مواقع (
connected-account-tokens،application-variable،application-registration-variable،signing-key-private-keys،sensitive-config-storage،totp-secrets). يُهمِل عامل تصفية SQL الصفوف الموجودة بالفعل على\<keyId>الجديد، لذلك يكون الأمر عديم الأثر التكراري (idempotent): يمكنك مقاطعته وإعادة تشغيله حسب الحاجة. يخرج بقيمة مختلفة عن الصفر إذا فشل أي صف — أعد تشغيله لإعادة المحاولة.خيار الوصف -s, --site \<site>حصر التنفيذ على موقع واحد فقط. -b, --batch-size \<n>عدد الصفوف في كل دفعة (الافتراضي 200، والحد الأقصى5000).-d, --dry-runفك التشفير + إعادة التشفير في الذاكرة، مع تخطي جملة UPDATE. -
إزالة المفتاح الاحتياطي (fallback) بمجرد أن يُظهِر الخيار
--dry-runعدم وجود صفوف متبقية: أزِلFALLBACK_ENCRYPTION_KEYوأعد التشغيل.
دعم APP_SECRET القديم
تستخدم النُسخ الأقدم التي لم تُعيِّن ENCRYPTION_KEY مطلقاً المتغيِّر APP_SECRET كمفتاح التشفير أثناء السكون (وكسرّ ملف تعريف الارتباط الخاص بالجلسة، المشتقّ منه). يُحفَظ هذا المسار لأغراض التوافق مع الإصدارات السابقة ولكنه مهمل (موقوف الدعم) — عيِّن متغير ENCRYPTION_KEY مخصَّصاً واتبع إجراء التدوير الموضَّح أعلاه للانتقال بعيداً عنه. يبقى APP_SECRET نفسه قيد الاستخدام للتحقق من رموز الوصول HS256 القديمة.