اشتراكات Stripe بدون كود: أخطاء تؤدي إلى تسرب الإيرادات
اشتراكات Stripe بدون كود: تجنّب تسرب الإيرادات عبر إصلاح معالجة الويبهوكات، منطق التجارب، حالات الاحتساب النسبي، وإعادة المحاولة عند فشل الدفعات باستخدام قائمة تدقيق QA.

أين يبدأ عادةً تسرب إيرادات الاشتراكات
تسرب الإيرادات في الاشتراكات نادراً ما يبدو درامياً. يظهر على شكل أخطاء صغيرة متكررة: عملاء يحتفظون بالوصول عندما لا ينبغي لهم ذلك، ترقيات لا تُحتسب بالكامل، أو اعتمادات تُطبَّق مرتين. قد يتكرر حافة خطأ واحد بصمت لأسابيع، خصوصاً مع توسع الاشتراكات.
حتى لو كنت تبني اشتراكات Stripe بدون كود، فالفوترة لا تزال تتضمن منطقاً. Stripe هو محرك الفوترة، لكن تطبيقك هو الذي يقرر ماذا يعني "نشط" الآن، متى تفتح الميزات، وكيف تتعامل مع عمليات التجديد وفشل الدفعات. أدوات اللاكود تُقلّل الكثير من العمل، لكنها لا تستطيع تخمين قواعدك.
معظم التسريبات تبدأ في أربعة أماكن:
- الويبهوكات غير المعالجة بشكل صحيح (أحداث مفقودة، مكررة، ترتيب خاطئ)
- التجارب التي لا تنتهي كما تتوقع (استمرار الوصول بعد الإلغاء أو عدم الدفع)
- الاحتساب النسبي عند تغيير الخطط (ترقيات وتخفيضات تُحتسب بأقل من اللازم، أو اعتمادات مفاجئة)
- الدفعات الفاشلة وإعادة المحاولة (تبقى الصلاحية خلال محاولة التحصيل، أو تُقطع مبكراً جداً)
نمط شائع هو "يعمل في اختبار المسار السعيد". تشترك، تحصل على وصول، تُدفع الفاتورة الأولى. ثم تحدث الحياة الحقيقية: بطاقة تفشل، عميل يرقّي في منتصف الدورة، شخص يلغي أثناء التجربة، أو Stripe تحاول الدفع ليلاً. إذا كان تطبيقك يفحص حقل واحد فقط (أو يستمع لحدث واحد فقط)، فقد تمنح وقتاً مجانياً أو تخلق اعتمادات مضاعفة عن طريق الخطأ.
إذا كنت تستخدم منصة مثل AppMaster، فمن السهل بناء الشاشات والتدفقات بسرعة. الخطر هو افتراض أن التدفق الافتراضي يعادل سياسة فوترة صحيحة. لا تزال بحاجة لتحديد قواعد الوصول والتحقق من أن خلفيتك تتفاعل مع أحداث Stripe باستمرار.
قرّر ما هو مصدر الحقيقة للوصول
إذا كنت تُشغّل اشتراكات Stripe بدون كود، فإن قراراً واحداً يمنع الكثير من التسريبات لاحقاً: أي نظام يقرر ما إذا كان المستخدم له وصول الآن.
هناك خياران شائعان:
- Stripe هو مصدر الحقيقة: تتحقق من حالة الاشتراك في Stripe كلما احتجت لتقرير الوصول.
- قاعدة بياناتك هي مصدر الحقيقة: تخزن حالة الوصول وتُحدّثها عند وقوع أحداث الفوترة.
الخيار الثاني عادة أسرع للتطبيق وأسهل للحفاظ على الاتساق عبر الويب والموبايل، بشرط أن تُحدّثه بشكل موثوق.
نهج عملي لكثير من المنتجات: Stripe هو مصدر الحقيقة للفوترة، وقاعدة بياناتك هي مصدر الحقيقة للوصول. لا تُعدِّل قاعدة البيانات يدوياً أو بأزرار واجهة مثل "وضع مدفوع". يجب أن تُشتق من أحداث Stripe (وتُعاد مصالحتها أحياناً).
للقيام بذلك، تحتاج إلى معرفات مستقرة. على الأقل، خزِّن الحقول التالية في سجل المستخدم أو الحساب:
- معرف عميل Stripe (من يدفع)
- معرف اشتراك Stripe (ما الخطة التي هم عليها)
- معرف الفاتورة الأخير (ما الذي فُوتر، بما في ذلك الاحتساب النسبي)
- معرف latest payment_intent (ما الذي حاول الدفع فعلياً)
بعد ذلك، عرّف ماذا يعني كل وضع اشتراك داخل منتجك. اكتبها كقواعد بسيطة قبل بناء الشاشات أو الأتمتة أو الويبهوكات.
سياسة افتراضية واضحة يستخدمها الكثيرون:
- active: وصول كامل
- trialing: وصول كامل حتى
trial_end، ثم إعادة التحقق من الحالة - past_due: وصول محدود (مثل قراءة فقط) لفترة سماح قصيرة
- unpaid: حظر الميزات المدفوعة؛ السماح بصفحة الفوترة وتصدير البيانات
- canceled: الاحتفاظ بالوصول حتى
period_endإذا سمحت بذلك، ثم الحظر
تجنّب الفجوات "مجانية للأبد". إذا سمحت بوصول كامل في past_due، فستحتاج إلى حد نهائي واضح (معتمد على تواريخ تخزنها)، لا مجرد "سنصلحها لاحقاً".
إذا كنت تبني في AppMaster، عامل قرار الوصول كمنطق أعمال: خزّن حالة الوصول الحالية على الحساب، حدّثها من أحداث Stripe، واجعل واجهة الويب والموبايل تقرأ ذلك الحقل الواحد باستمرار. هذا يحافظ على سلوك متوقع حتى لو وصلت أحداث Stripe متأخرة أو خارجة عن الترتيب.
الويبهوكات: أنماط تمنع الأحداث المفقودة والمعالجات المزدوجة
الويبهوكات هي المكان الهادئ الذي تبدأ منه تسريبات الإيرادات. قد يرسل Stripe الأحداث أكثر من مرة، أو يرسلها خارج الترتيب، أو يصلها بعد ساعات. عامل كل ويبهوك على أنه "قد يكون متأخراً" و"قد يكون مكرراً"، وصمم تحديثات الوصول كي تظل صحيحة على أي حال.
الأحداث المهمة (والتي يمكنك عادةً تجاهلها)
التزم بمجموعة صغيرة من الأحداث التي تمثل تغيّرات حالة الاشتراك الحقيقية. لمعظم الإعدادات، هذه تغطي تقريباً كل ما تحتاج:
checkout.session.completed(عندما تستخدم Checkout لبدء اشتراك)customer.subscription.created,customer.subscription.updated,customer.subscription.deletedinvoice.paid(اللحظة التي تُدفع فيها فترة الفوترة فعلياً)invoice.payment_failed(اللحظة التي لا تُدفع فيها)
كثير من الفرق يبالغون في ردة فعلهم لأحداث صاخبة مثل charge.updated أو payment_intent.* وينتهون بقواعد متضاربة. إذا كنت تتعامل مع الفواتير والاشتراكات جيداً، فالأحداث ذات المستوى الأدنى غالباً ما تضيف لبساً.
التكرارية (idempotency): أوقف الفتح المزدوج عندما يعيد Stripe المحاولة
Stripe يعيد إرسال الويبهوكات. إذا "منحت الوصول" في كل مرة ترى فيها invoice.paid، فبعض العملاء سيحصلون على وقت إضافي، اعتمادات مكررة، أو امتيازات متكررة.
نمط بسيط يعمل:
- خزّن
event.idكمُعالَج قبل أي إجراء لا رجعة فيه - إذا رأيت نفس
event.idمرة أخرى، انتهِ مبكراً - سجِّل ما تغيّر (المستخدم/الحساب، معرف الاشتراك، حالة الوصول السابقة، حالة الوصول الجديدة)
في AppMaster، هذا يتوافق بسلاسة مع جدول قاعدة بيانات بالإضافة إلى تدفُّق Business Process الذي يتحقق من "هل عالجناها بالفعل؟" قبل تحديث الوصول.
ترتيب الأحداث: صمّم للاستقبال المتأخر والخارج عن الترتيب
لا تفترض أن customer.subscription.updated سيصل قبل invoice.paid، أو أنك سترى كل حدث بالترتيب. استند في الوصول إلى أحدث حالة اشتراك وفاتورة معروفة، لا إلى ما كنت تتوقع حدوثه بعد ذلك.
عندما يبدو شيء ما غير متسق، استعلم عن الاشتراك الحالي من Stripe وقم بالمصالحة.
أيضاً خزّن الحمولة الخام للويبهوك (على الأقل لمدة 30 إلى 90 يوماً). عندما يسأل الدعم "لماذا فقدت الوصول؟" أو "لماذا فُوِّت علّي مرتين؟"، يحوّل سجل التدقيق هذا اللغز إلى إجابة.
أخطاء الويبهوك التي تخلق وصولاً مجانياً أو لبساً في الفوترة
الويبهوكات هي الرسائل التي يرسلها Stripe عندما يحدث شيء فعلياً. إذا تجاهل تطبيقك هذه الرسائل أو تفاعل مع اللحظة الخاطئة، يمكنك منح الوصول مجاناً أو التسبب في سلوك فوترة غير متناسق.
خطأ شائع هو منح الوصول عندما يكتمل Checkout بدلاً من عندما تُجمع النقود. "اكتمال Checkout" قد يعني أن العميل بدأ اشتراكاً، لا أن الفاتورة الأولى دُفعت. البطاقات تفشل، و3D Secure قد يُهمل، وبعض طرق الدفع تُسوى لاحقاً. من أجل الوصول، اعتبر invoice.paid (أو payment_intent ناجح مرتبط بالفاتورة) كلحظة لتمكين الميزات.
مصدر آخر للتسريبات هو الاستماع فقط لمسار السعادة. الاشتراكات تتغير مع الوقت: ترقيات، تخفيضات، إلغاءات، إيقاف مؤقت، وحالات متأخرة الدفع. إذا لم تُعالج أبداً تحديثات الاشتراك، فقد يحتفظ عميل ملغٍ بالوصول لأسابيع.
أربع مطبات لتراقبها:
- اعتماد العميل (الواجهة الأمامية) لإخبارك أن الاشتراك نشط، بدلاً من تحديث قاعدة البيانات من الويبهوكات
- عدم التحقق من توقيعات الويبهوك، مما يجعل من السهل للطلبات المزيفة قلب حالة الوصول
- خلط أحداث الاختبار والبيئة الحية (مثلاً قبول ويبهوكات وضع الاختبار في الإنتاج)
- معالجة نوع حدث واحد وافتراض أن الباقي "سينجح بنفسه"
فشل عملي في العالم الحقيقي: يكمل العميل Checkout، يفتح تطبيقك الميزة المميزة، وتفشل الفاتورة الأولى. إذا لم يُعالَج حدث الفشل، يبقى العميل مميزاً دون دفع.
إذا بنت اشتراكات Stripe بدون كود على منصة مثل AppMaster، فالهدف هو نفسه: احتفظ بسجل خادمي واحد للوصول، وغيرّه فقط عندما تؤكد ويبهوكات Stripe أن الدفع نجح أو فشل أو أن حالة الاشتراك تغيرت.
التجارب: تجنّب الوقت المجاني الذي لا ينتهي
التجربة ليست مجرد "فوترة مجانية". إنها وعد واضح: ماذا يمكن للعميل استخدامه، لِمَدةٍ، وماذا يحدث بعد ذلك. أكبر خطر هو معاملة التجربة كوسم في الواجهة بدلاً من قاعدة وصول محددة زمنياً.
قرّر ماذا يعني "وصول التجربة" في منتجك. هل هو وصول كامل، أم مقاعد محدودة، أو ميزات أو استخدام مقيد؟ قرّر كيف ستذكّر الأشخاص قبل انتهاء التجربة (بريد إلكتروني، لافتة داخل التطبيق)، وماذا تُظهر صفحة الفوترة عندما لم يضيف العميل بطاقة.
اربط الوصول بتواريخ يمكنك التحقق منها، لا بمتغير محلي مثل is_trial = true. امنح وصول التجربة عندما تقول Stripe أن الاشتراك خُلق مع تجربة، وأزل وصول التجربة عند انتهاءها إلا إذا كان الاشتراك نشطاً ومدفوعاً. إذا خزَّن تطبيقك trial_ends_at، حدّثه من أحداث Stripe، لا من نقرة مستخدم.
توقيت جمع البطاقة هو المكان الذي يتسلل منه "المجاني للأبد" عادة. إذا بدأت تجارب بدون جمع وسيلة دفع، خطّط لمسار التحويل:
- عرض خطوة واضحة "إضافة وسيلة دفع" قبل نهاية التجربة
- قرّر ما إذا كنت تسمح ببدء التجربة بدون بطاقة على الإطلاق
- إذا فشل الدفع عند التحويل، خفّض الوصول فوراً أو بعد فترة سماح قصيرة
- دائماً أظهر تاريخ نهاية التجربة داخل التطبيق بالضبط
الحواف مهمة لأن التجارب تُعدّل. قد يمدّد الدعم تجربة، أو يلغي المستخدم في اليوم الأول. كما يرقّي المستخدمون أثناء التجربة ويتوقعون الخطة الجديدة فوراً. اختر قواعد بسيطة وابقها ثابتة: الترقية أثناء التجربة يجب أن تحتفظ بتاريخ نهاية التجربة، أو تنهي التجربة وتبدأ الفوترة الآن. أياً كان اختيارك، اجعله متوقعاً ومرئياً.
نمط فشل شائع: تمنح الوصول عند نقر المستخدم "ابدأ التجربة"، لكنك تزيله فقط عند نقره "إلغاء". إذا أغلق الصفحة أو فشل ويبهوكك، يظل لديهم الوصول. في تطبيق لاكود (بما في ذلك AppMaster)، استند الوصول إلى حالة الاشتراك وطوابع نهاية التجربة المستلمة من ويبهوكات Stripe، لا إلى علم يدوي وضعته الواجهة الأمامية.
الاحتساب النسبي (Proration): إيقاف التقليل غير المقصود في التحصيل أثناء تغيير الخطط
الاحتساب النسبي هو ما يحدث عندما يغير العميل اشتراكه في منتصف الدورة ويعدِّل Stripe الفاتورة بحيث يدفع فقط مقابل ما استخدمه. قد ينشئ Stripe فاتورة احتسابية عندما يرقّي أحدهم، يخفض، يغيّر الكمية (مثل المقاعد)، أو ينتقل إلى سعر مختلف.
أشهر تسرب للإيرادات هو التقليل في التحصيل أثناء الترقيات. يحدث عندما يمنح تطبيقك ميزات الخطة الجديدة فوراً، لكن تغيير الفوترة يسري لاحقاً، أو فاتورة الاحتساب لم تُدفع أبداً. يحصل العميل على الخطة الأفضل مجاناً حتى التجديد التالي.
اختر سياسة احتساب نسبي والتزم بها
الترقيات والتخفيضات لا ينبغي أن تُعامل بنفس المنهج ما لم تكن تريد ذلك عن قصد.
مجموعة سياسات بسيطة ومتسقة:
- الترقيات: تطبّق فوراً، احتسب الفرق الآن
- التخفيضات: تطبّق عند التجديد التالي (لا تعيد مبالغ منتصف الدورة)
- زيادات الكمية (مقاعد أكثر): تطبّق فوراً مع احتساب نسبي
- تقليل الكمية: يطبق عند التجديد
- اختياري: السماح بـ"بدون احتساب" فقط لحالات خاصة (مثل عقود سنوية)، وليس عن طريق الخطأ
إذا كنت تبني اشتراكات Stripe بدون كود في AppMaster، تأكد أن تدفق تغيير الخطة وقواعد التحكم في الوصول تطابق السياسة. إذا كانت الترقيات تُحسب الآن، فلا تفتح الميزات حتى تؤكد Stripe أن فاتورة الاحتساب دُفعت.
التغييرات منتصف الدورة قد تكون معقّدة مع المقاعد أو مستويات الاستخدام. قد يضيف فريق 20 مقعداً في اليوم 25، ثم يزيل 15 مقعداً في اليوم 27. إذا كان منطقك غير متسق، يمكنك منح مقاعد إضافية دون تحصيل أو إنشاء اعتمادات مربكة تؤدي إلى استردادات وتذاكر دعم.
اشرح الاحتساب النسبي قبل أن ينقر العميل
المناظرات حول الاحتساب النسبي غالباً ما تنشأ من فواتير مفاجئة، لا نية سيئة. أضف جملة قصيرة بجانب زر التأكيد تطابق سياستك وتوقيتك:
- "الترقيات تبدأ اليوم وسيتم تحصيل مبلغ احتساب نسبي الآن."
- "التخفيضات تبدأ في تاريخ التجديد التالي."
- "إضافة المقاعد تُحتسب فوراً؛ إزالة المقاعد تسري في الدورة التالية."
توقعات واضحة تقلل النزاعات، الاستردادات، ورسائل "لماذا تم تحميلي مرتين؟".
الدفعات الفاشلة وإعادة المحاولة: ضبط الدننج والوصول بشكل صحيح
الدفعات الفاشلة هي المكان الذي يتسرب فيه الإعداد للاشتراكات بصمت. إذا ترك تطبيقك الوصول مفتوحاً إلى الأبد بعد فشل الشحنة، فأنت تقدم الخدمة دون دفع. إذا قطعت الوصول مبكراً جداً، فتصنع تذاكر دعم ومعدل فقدان عملاء غير ضروري.
اعرف الحالات التي تهم
بعد فشل الشحنة، يمكن أن ينقل Stripe الاشتراك عبر past_due ولاحقاً إلى unpaid (أو الإلغاء، اعتماداً على الإعدادات). عامل هذه الحالات بشكل مختلف. past_due عادة تعني أن العميل قابل للاسترداد وStripe يعيد المحاولة. unpaid عموماً تعني أن الفاتورة لا تُدفع ويجب عليك إيقاف الخدمة.
خطأ شائع في تشغيل اشتراكات Stripe بدون كود هو فحص حقل واحد فقط (مثل "الاشتراك نشط") وعدم التفاعل مطلقاً مع فشل الفواتير. يجب أن يتبع الوصول إشارات الفوترة، لا الافتراضات.
خطة دننج بسيطة تحمي الإيرادات
قرّر جدول إعادة المحاولة وفترة السماح مقدماً، ثم رمزها كقواعد يمكن لتطبيقك فرضها. Stripe يتعامل مع إعادة المحاولة إذا كانت مُكوَّنة، لكن تطبيقك ما زال يقرر ماذا يحدث للوصول خلال نافذة إعادة المحاولة.
نموذج عملي:
- عند
invoice.payment_failed: وسم الحساب كـ "مشكلة دفع"، احتفظ بالوصول لفترة سماح قصيرة (مثلاً 3 إلى 7 أيام) - بينما الاشتراك في حالة
past_due: أظهر لافتة داخل التطبيق وأرسل رسالة "حدّث البطاقة" - عندما ينجح الدفع (
invoice.paidأوinvoice.payment_succeeded): أزل وسم مشكلة الدفع واستعد الوصول الكامل - عندما يصبح الاشتراك
unpaid(أو يُلغى): انتقل إلى وضع قراءة فقط أو احظر الإجراءات الأساسية، لا تكتفِ بإخفاء صفحة الفوترة - سجّل حالة الفاتورة الأخيرة وموعد إعادة المحاولة التالي حتى يرى الدعم ما يحدث
تجنّب فترة سماح لانهائية بتخزين موعد نهائي صارم على جانبك. مثلاً، عند استلام أول حدث فشل، احسب طابع نهاية السماح وفرضه حتى لو تأخرت الأحداث اللاحقة أو فُقدت.
لمسار "تحديث البطاقة"، لا تفترض أن المشكلة حُلّت عندما يدخل العميل تفاصيل جديدة. أكد الاسترداد فقط بعد أن تُظهر Stripe فاتورة مدفوعة أو حدث دفعة ناجح. في AppMaster، يمكن أن يكون هذا Business Process واضح: عندما يصل ويبهوك نجاح الدفع، قم بإعادة المستخدم إلى active، افتح الميزات، وأرسل رسالة تأكيد.
سيناريو نموذجي: رحلة عميل واحدة، أربعة مطبات شائعة
مايا تشترك في تجربة 14 يوماً. تدخل بطاقة، تبدأ التجربة، ترقي في اليوم 10، ثم يرفض بنكها لاحقاً التجديد. هذا أمر طبيعي، وهو بالضبط المكان الذي تحدث فيه تسريبات الإيرادات.
جدول زمني خطوة بخطوة (وماذا يجب أن يفعل تطبيقك)
- بدء التجربة: ينشئ Stripe الاشتراك ويحدد نهاية التجربة. عادة سترى
customer.subscription.createdوربما فاتورة مقبلة حسب الإعداد. يجب أن يمنح تطبيقك الوصول لأن الاشتراك في تجربة، ويجب أن يسجّل موعد انتهاء التجربة حتى يتغير الوصول تلقائياً.
مطبة 1: منح الوصول عند "نجاح التسجيل" فقط، ثم عدم تحديثه عند انتهاء التجربة.
- الترقية أثناء التجربة: تغيّر مايا من Basic إلى Pro في اليوم 10. يحدث Stripe تحديثاً للاشتراك وقد ينشئ فاتورة أو احتساباً نسبياً. قد ترى
customer.subscription.updated,invoice.created,invoice.finalized، ثمinvoice.paidإذا جُمعت النقود.
مطبة 2: اعتبار "تغيير الخطة" وصولاً مدفوعاً فوراً حتى لو كانت الفاتورة مفتوحة أو فشل الدفع لاحقاً.
- التجديد: في اليوم 14 تبدأ الفترة المدفوعة الأولى، ثم في الشهر التالي تُحاول فاتورة التجديد الدفع.
مطبة 3: الاعتماد على ويبهوك واحد وفقدان الآخرين، فتفشل إما في إزالة الوصول بعد invoice.payment_failed أو تزيل الوصول بعد invoice.paid بسبب التكرارات وترتيب الأحداث.
- فشل البطاقة: يعلّم Stripe أن الفاتورة غير مدفوعة ويبدأ محاولات إعادة الدفع حسب إعداداتك.
مطبة 4: قفل المستخدم فوراً بدلاً من استخدام فترة سماح قصيرة ومسار "تحديث البطاقة" واضح.
ما الذي يجب تخزينه حتى يستطيع الدعم حل المشكلات بسرعة
احتفظ بسجل تدقيق صغير: معرف عميل Stripe، معرف الاشتراك، الحالة الحالية، trial_end, current_period_end, معرف الفاتورة الأخير، تاريخ آخر دفعة ناجحة، وآخر معرف ويبهوك تمت معالجته مع الطابع الزمني.
عندما تتواصل مايا مع الدعم أثناء المشكلة، يجب أن يستطيع فريقك الإجابة بسرعة على سؤالين: ماذا تقول Stripe الآن، وماذا طبّق تطبيقنا آخر مرة؟
قائمة تدقيق QA: تحقق من سلوك الفوترة قبل الإطلاق
عامل الفوترة كميزة يجب اختبارها، لا كمفتاح تضبطه. معظم تسرب الإيرادات يحدث في الفجوات بين أحداث Stripe وما يقرره تطبيقك عن الوصول.
ابدأ بفصل "هل يستطيع Stripe التحصيل؟" عن "هل يمنح التطبيق الوصول؟" واختبر كلاهما في نفس البيئة التي ستطلق فيها.
فحوصات الإعداد قبل الإطلاق
- تأكد من فصل الاختبار والبيئة الحية: المفاتيح، نقاط نهاية الويبهوك، المنتجات/الأسعار، متغيرات البيئة
- تحقق من أمان نقاط نهاية الويبهوك: تفعيل التحقق من التوقيع، ورفض الأحداث غير الموقعة أو المشوشة
- افحص idempotency: الأحداث المكررة لا تخلق امتيازات أو فواتير أو رسائل بريد إضافية
- اجعل السجلات قابلة للاستخدام: خزّن معرف الحدث، العميل، الاشتراك، وقرار الوصول النهائي
- تحقق من التطابق: كل حساب مستخدم يطابق تماماً عميل Stripe واحد (أو لديك قاعدة واضحة لعدة عملاء)
في AppMaster، هذا عادة يعني تأكيد تكامل Stripe، إعدادات البيئة، وتدفّقات Business Process التي تسجّل أثر تدقيق نظيف لكل حدث ويبهوك وتغيير وصول ناتج.
حالات اختبار سلوك الاشتراك
قم بتشغيل هذه السيناريوهات كجلسة QA مُوجَّهة قصيرة. استخدم أدواراً حقيقية (مستخدم عادي، مسؤول) واكتب ماذا يعني "الوصول مُفعل/معطل" في منتجك.
- التجارب: ابدأ تجربة، ألغِ أثناء التجربة، اتركها تنتهي، مددها مرة، أكد أن التحويل يحدث فقط عندما ينجح الدفع
- الاحتساب النسبي: ارقِّ في منتصف الدورة، خفِّض في منتصف الدورة، قم بتغييرين في نفس اليوم؛ أكد أن الفاتورة والوصول يطابقان سياستك
- الاعتمادات/الاستردادات: امنح اعتماداً أو ردّ مبلغ وتحقق من أنك لا تحتفظ بالوصول المميز للأبد (أو تزيله مبكراً جداً)
- الدفعات الفاشلة: حاكي فشل تجديد، تحقق من توقيت إعادة المحاولة وفترة السماح، أكد متى يُقيَّد أو يُزال الوصول
- الاسترداد: بعد فشل دفعة، أكمل الدفع وتأكد أن الوصول يعود فوراً (وعلى نحو لا يتكرر)
لكل اختبار، سجّل ثلاث حقائق: جدول أحداث Stripe، حالة قاعدة بياناتك، وما الذي يستطيع المستخدم فعله فعلياً في التطبيق. عندما تختلف هذه الثلاثة، لقد وجدت التسريب.
الخطوات التالية: نفّذ بأمان وحافظ على تنبؤ الفوترة
اكتب قواعد الفوترة بلغة بسيطة واحتفظ بها محددة: متى يبدأ الوصول، متى يتوقف، ماذا يُعتبر "مدفوعاً"، كيف تنتهي التجارب، وماذا يحدث عند تغيّر الخطط. إذا قرأ شخصان القواعد وتخيّلا نتائج مختلفة، فسيتسرّب المال من سير العمل.
حوّل تلك القواعد إلى خطة اختبار قابلة للتكرار تجريها في كل مرة تغيّر فيها منطق الفوترة. بضعة عملاء اختبار مخصصين على Stripe ونص ثابت أفضل من "التجول والنظر".
أثناء الاختبار، احفظ أثر تدقيق. الدعم والمالية سيحتاجان إجابات سريعة مثل "لماذا احتفظ هذا المستخدم بالوصول؟" أو "لماذا حُمِلت علي مرتين؟" سجّل تغيّرات الاشتراك والفاتورة الأساسية (الحالة، تواريخ الفترة الحالية، نهاية التجربة، الفاتورة الأخيرة، نتيجة payment_intent)، وخزّن معرف حدث الويبهوك حتى تستطيع إثبات ما حدث وتجنب معالجة نفس الحدث مرتين.
إذا كنت تنفّذ ذلك بدون كود، يمكن لـ AppMaster (appmaster.io) مساعدتك في الحفاظ على البنية متسقة. يمكنك نمذجة بيانات الفوترة في Data Designer (PostgreSQL)، معالجة ويبهوكات Stripe في Business Process Editor مع فحوصات idempotency، والتحكم في الوصول بحقل "مصدر الحقيقة" واحد تقرأه واجهة الويب والموبايل.
اختتم بتجربة جافة تبدو كالحياة الحقيقية: زميل يسجل، يستخدم التطبيق، يرقّي، تفشل دفعة، ثم يصححها. إذا طابق كل خطوة قواعدك المكتوبة، فأنت جاهز.
الخطوة التالية: جرِّب بناء تدفق اشتراك Stripe بسيط في AppMaster، ثم شغّل قائمة التحقق QA قبل الإطلاق.


