مرجع الترخيص

فئات وواجهات LVL

يسرد الجدول 1 جميع الملفات المصدر في "مكتبة التحقّق من الترخيص" (LVL) المتاحة من خلال حزمة تطوير البرامج (SDK) لنظام التشغيل Android. تُعد كل الملفات جزءًا من حزمة com.android.vending.licensing.

الجدول 1. ملخص لفصول مكتبة LVL وواجهاتها.

الفئة الاسم الوصف
التحقّق من الترخيص ونتائجه أداة التحقّق من التراخيص الفئة التي تنشئ مثيلاً لها (أو فئة فرعية) لبدء التحقّق من الترخيص.
LicenseCheckerCallback الواجهة التي تستخدمها لمعالجة نتيجة التحقّق من الترخيص.
السياسة السياسة الواجهة التي تنفّذها لتحديد ما إذا كان سيتم السماح بالوصول إلى التطبيق استنادًا إلى استجابة الترخيص.
سياسة إدارة الخادم عملية التنفيذ التلقائية للقاعدة Policy. تستخدم هذه السياسة الإعدادات التي يوفّرها خادم الترخيص لإدارة التخزين المحلي لبيانات الترخيص وصلاحية الترخيص وإعادة المحاولة.
سياسة متشددة طريقة تنفيذ Policy بديلة ينفذ الترخيص استنادًا إلى استجابة الترخيص المباشرة من الخادم فقط. ليس هناك تخزين مؤقت أو طلب إعادة المحاولة.
تشويش البيانات
(اختياري)
أداة تشويش الواجهة التي تنفّذها إذا كنت تستخدم واجهة Policy (مثل ServerManagedPolicy) التي تخزّن بيانات استجابة الترخيص في متجر دائم. يطبق خوارزمية التشويش على ترميز وفك ترميز البيانات التي تتم كتابتها أو قراءتها.
خوارزمية التشفير المتقدّم (AES) هو التطبيق التلقائي لأداة Obfuscator الذي يستخدم خوارزمية التشفير AES/فك التشفير لتشويش البيانات أو إزالة تشويشها.
الحد الأقصى لعدد الأجهزة
(اختياري)
Devicelimiter الواجهة التي تنفّذها إذا أردت حصر استخدام أحد التطبيقات بجهاز معين. تم استدعاء الدالة من License Verificationator. لا يُنصَح بتنفيذ Devicelimiteder في معظم التطبيقات لأنّها تتطلّب خادم خلفية وقد تتسبب في فقدان المستخدم لإمكانية الوصول إلى التطبيقات المُرخَّصة، ما لم يتم تصميمها بحرص.
NullDevicelimiter عملية تنفيذ Devicelimiter التلقائية التي لا تعمل (يسمح بالوصول إلى جميع الأجهزة).
تطبيق أساسي للمكتبة، لا حاجة إلى أي دمج بيانات الاستجابة الفئة التي تحتوي على حقول استجابة الترخيص.
أداة التحقّق من صحة التراخيص الفئة التي تفك تشفير استجابة تم استلامها من خادم الترخيص وتتحقق منها.
التحقّق من الاستثناء فئة تشير إلى الأخطاء التي تحدث عند التحقّق من سلامة البيانات التي يديرها برنامج Obfuscator.
تفضيل فئة الأداة التي تكتب/تقرأ البيانات التي تم تشويشها في متجر SharedPreferences الخاص بالنظام.
ILicensingService واجهة IPC أحادية الاتجاه التي يتم من خلالها تمرير طلب التحقق من الترخيص إلى عميل Google Play.
ILicenseResultListener تنفيذ معاودة الاتصال IPC الأحادي الاتجاه الذي يتلقى التطبيق من خلاله استجابة غير متزامنة من خادم الترخيص.

استجابة الخادم

يسرد الجدول 2 جميع حقول استجابة الترخيص التي يعرضها خادم الترخيص.

الجدول 2. ملخص لحقول استجابة الترخيص التي يعرضها خادم Google Play

الحقل الوصف
responseCode رمز الاستجابة الذي يعرضه خادم الترخيص. يتم توضيح رموز الاستجابة في رموز استجابة الخادم.
signedData يشير ذلك المصطلح إلى تسلسل سلاسل يضم البيانات التي يعرضها خادم الترخيص، على النحو التالي: responseCode|nonce|packageName|versionCode|userId|timestamp:extras.
  • responseCode: رمز الاستجابة الذي يعرضه خادم الترخيص
  • nonce: رقم تعريف الطلب
  • packageName: اسم حزمة التطبيق المطلوب التحقّق من الترخيص الخاص به
  • versionCode: رمز إصدار التطبيق المطلوب التحقّق من الترخيص له.
  • userId: رقم تعريف فريد للمستخدم لكل تطبيق، حيث يحصل المستخدم نفسه على معرّف مختلف لتطبيق مختلف.
  • timestamp: عدد المللي ثانية من حقبة 1970-01-01 00:00:00 حسب التوقيت العالمي المنسَّق (UTC) للطلب.
  • extras: معلومات إضافية للمساعدة في إدارة ترخيص التطبيق. الحقول الإضافية موضَّحة في العناصر الإضافية لاستجابة الخادم.
signature توقيع signedData باستخدام مفتاح خاص بالتطبيق.

رموز استجابة الخادم

يسرد الجدول 3 جميع رموز استجابة الترخيص المتوافقة مع خادم الترخيص. بشكل عام، يجب أن يعالج التطبيق جميع رموز الاستجابة هذه. وبشكل تلقائي، توفّر فئة LicensePolicyator في LVL كل عمليات المعالجة اللازمة لرموز الاستجابة هذه.

الجدول 3. ملخص لرموز الاستجابة التي أرجعها خادم Google Play في استجابة الترخيص.

رمز الاستجابة تمثيل القيمة الصحيحة الوصف هل تم التوقيع؟ محتوى إضافي التعليقات
LICENSED 0 تم ترخيص التطبيق للمستخدم. اشترى المستخدم التطبيق، أو يملك إذنًا بتنزيل وتثبيت الإصدار ألفا أو التجريبي من التطبيق نعم VT، GT، GR السماح بالوصول وفقًا لقيود Policy
LICENSED_OLD_KEY 2 يتم ترخيص التطبيق للمستخدم، ولكن يتوفر إصدار محدّث من التطبيق موقَّع بمفتاح مختلف. نعم VT وGT وGR وUT يمكنك السماح بالوصول وفقًا لقيود Policy إذا أردت ذلك.

يمكن أن يشير إلى أن زوج المفاتيح المستخدم في إصدار التطبيق المثبت غير صالح أو مخترَق. يمكن للتطبيق السماح بالوصول إذا لزم الأمر أو إبلاغ المستخدم بتوفّر ترقية والحدّ من الاستخدام الإضافي حتى الترقية.

NOT_LICENSED 1 لم يتم ترخيص التطبيق للمستخدم. لا عدم السماح بالوصول:
ERROR_CONTACTING_SERVER 257 خطأ محلي: تعذّر على تطبيق Google Play الوصول إلى خادم الترخيص، ربما بسبب مشاكل في مدى توفُّر الشبكة. لا إعادة محاولة فحص الترخيص وفقًا لحدود إعادة المحاولة Policy.
ERROR_SERVER_FAILURE 4 خطأ في الخادم - لم يتمكن الخادم من تحميل زوج مفاتيح التطبيق للترخيص. لا إعادة محاولة فحص الترخيص وفقًا لحدود إعادة المحاولة Policy.
ERROR_INVALID_PACKAGE_NAME 258 خطأ محلي - طلب التطبيق فحص الترخيص لحزمة غير مثبتة على الجهاز. لا عدم إعادة محاولة التحقّق من الترخيص

يحدث هذا عادةً بسبب خطأ في التطوير.

ERROR_NON_MATCHING_UID 259 خطأ محلي - طلب التطبيق فحص الترخيص لحزمة لا يتطابق معرفها الفريد (الحزمة أو زوج معرف المستخدم) مع التطبيق مقدم الطلب. لا عدم إعادة محاولة التحقّق من الترخيص

يحدث هذا عادةً بسبب خطأ في التطوير.

ERROR_NOT_MARKET_MANAGED 3 خطأ في الخادم - لم يتعرّف Google Play على التطبيق (اسم الحزمة). لا عدم إعادة محاولة التحقّق من الترخيص

يمكن أن تشير إلى أنّ التطبيق لم يتم نشره من خلال Google Play أو إلى حدوث خطأ في التطوير في تنفيذ الترخيص.

ملاحظة: كما هو موثق في إعداد بيئة الاختبار، يمكن إلغاء رمز الاستجابة يدويًا لمطوِّر التطبيق وأي مستخدمي اختبار مسجَّلين عبر Google Play Console.

ملاحظة: في السابق، كان بإمكانك اختبار أحد التطبيقات من خلال تحميل إصدار "مسودّة" غير منشور. لم تعُد هذه الوظيفة متاحة، وبدلاً من ذلك، عليك نشرها على قناة التوزيع ألفا أو التجريبية. لمزيد من المعلومات، يُرجى الاطّلاع على مسودّة التطبيقات لم تعُد متوافقة.

الإضافات الإضافية لاستجابة الخادم

لمساعدة تطبيقك في إدارة الوصول إلى التطبيق خلال فترة ردّ أموال التطبيق وتوفير معلومات أخرى، يضمّن خادم الترخيص عدة أجزاء من المعلومات في ردود الترخيص. وعلى وجه التحديد، توفّر الخدمة القيم المقترَحة لفترة صلاحية ترخيص التطبيق وفترة السماح لإعادة المحاولة والحد الأقصى لعدد مرات إعادة المحاولة المسموح به وغير ذلك من الإعدادات. إذا كان تطبيقك يستخدم ملفات توسيع APK، ستتضمّن الاستجابة أيضًا أسماء الملفات وأحجامها وعناوين URL. ويُلحق الخادم الإعدادات كأزواج المفتاح/القيمة في حقل "إضافية" لاستجابة الترخيص.

يمكن لأي عملية تنفيذ للسمة Policy استخراج إعدادات الإضافات من استجابة الترخيص واستخدامها حسب الحاجة. إنّ آلية تنفيذ Policy التلقائية في LVL، ServerManagedPolicy، هي بمثابة طريقة تنفيذ عملية ورسم توضيحي لكيفية الحصول على الإعدادات وتخزينها واستخدامها.

الجدول 4. ملخّص إعدادات إدارة التراخيص التي يوفّرها خادم Google Play في استجابة الترخيص.

المزيد!الوصف
VT الطابع الزمني لصلاحية الترخيص تحدد التاريخ/الوقت الذي تنتهي عنده استجابة الترخيص الحالي (المخزَّن مؤقتًا) ويجب إعادة التحقّق منها على خادم الترخيص. يُرجى الاطّلاع على القسم أدناه حول فترة صلاحية الترخيص.
GT الطابع الزمني لفترة السماح تحدّد هذه السياسة نهاية الفترة التي قد تسمح السياسة خلالها بالوصول إلى التطبيق، حتى إذا كانت حالة الاستجابة هي RETRY.

يدير الخادم القيمة، لكن القيمة المعتادة تكون 5 أيام أو أكثر. يُرجى الاطِّلاع على القسم أدناه حول فترة إعادة المحاولة والحد الأقصى لعدد إعادة المحاولة.

GR الحدّ الأقصى لعدد عمليات إعادة المحاولة تحدِّد هذه السياسة عدد عمليات التحقّق المتتالية المتعلّقة بتراخيص RETRY التي يجب أن يسمح بها Policy، وذلك قبل منع المستخدم من الوصول إلى التطبيق.

يدير الخادم القيمة، لكن القيمة النموذجية تكون "10" أو أعلى. يُرجى الاطِّلاع على القسم أدناه حول فترة إعادة المحاولة والحد الأقصى لعدد إعادة المحاولة.

UT الطابع الزمني للتحديث. تحدد اليوم/الوقت الذي تم فيه تحميل آخر تحديث لهذا التطبيق ونشره.

يعرض الخادم هذه البيانات الإضافية فقط لردود LICENSED_OLD_KEYS، وهي للسماح لـ Policy بتحديد مقدار الوقت المنقضي منذ نشر تحديث باستخدام مفاتيح ترخيص جديدة قبل رفض وصول المستخدم إلى التطبيق.

FILE_URL1 أو FILE_URL2 عنوان URL لملف توسيع (1 هو للملف الرئيسي، 2 هو ملف التصحيح). استخدِم هذا الخيار لتنزيل الملف عبر بروتوكول HTTP.
FILE_NAME1 أو FILE_NAME2 اسم ملف التوسيع (1 هو للملف الرئيسي، 2 هو ملف التصحيح). يجب استخدام هذا الاسم عند حفظ الملف على الجهاز.
FILE_SIZE1 أو FILE_SIZE2 حجم الملف بالبايت (1 هو الملف الرئيسي، 2 هو ملف التصحيح). واستخدم هذا التطبيق للمساعدة في التنزيل والتأكد من توفّر مساحة كافية على موقع التخزين المشترك للجهاز قبل التنزيل.

مدة صلاحية الترخيص

يضبط خادم الترخيص في Google Play مدة صلاحية الترخيص لجميع التطبيقات التي تم تنزيلها. وتعبِّر الفترة عن الفترة الزمنية التي يجب خلالها اعتبار حالة ترخيص التطبيق غير متغيرة وقابلة للتخزين المؤقت من خلال Policy للترخيص في التطبيق. يعرض خادم الترخيص مدة الصلاحية استجابةً لجميع فحوصات التراخيص، مع إلحاق طابع زمني لانتهاء الصلاحية بالاستجابة كمدة إضافية ضمن المفتاح VT. يمكن لـ Policy استخراج قيمة مفتاح VT واستخدامها للسماح بالوصول المشروط إلى التطبيق بدون إعادة التحقّق من الترخيص، وذلك إلى أن تنتهي صلاحية مدة الصلاحية.

تشير صلاحية الترخيص إلى Policy للترخيص عندما يكون مطلوبًا منه إعادة التحقّق من حالة الترخيص مع خادم الترخيص. ولا يهدف إلى الإشارة ضمنًا إلى ما إذا كان التطبيق مرخصًا للاستخدام أم لا. وهذا لا يعني أنّه عند انتهاء صلاحية فترة صلاحية ترخيص التطبيق، لا يعني ذلك أنّ التطبيق لم يعُد مرخَّصًا للاستخدام، بل يشير فقط إلى أنّه على Policy إعادة التحقّق من حالة الترخيص مع الخادم. بناءً على ذلك، ما دامت مدة صلاحية الترخيص لم تنتهِ، يُسمح لـ Policy بتخزين حالة الترخيص الأولية مؤقتًا على الجهاز وعرض حالة الترخيص المُخزَّنة مؤقتًا بدلاً من إرسال فحص ترخيص جديد إلى الخادم.

ويدير خادم الترخيص مدة الصلاحية كوسيلة لمساعدة التطبيق في تنفيذ الترخيص على نحو سليم خلال فترة رد الأموال التي يوفرها Google Play للتطبيقات المدفوعة. تحدّد مدة الصلاحية استنادًا إلى ما إذا كان تم شراء التطبيق أم لا، وإذا كان الأمر كذلك، كانت المدة التي تسبقه. وعلى وجه التحديد، يضبط الخادم فترة الصلاحية على النحو التالي:

  • بالنسبة إلى التطبيق المدفوع، يضبط الخادم مدة صلاحية الترخيص الأولية حتى تظل استجابة الترخيص صالحة ما دام التطبيق قابلاً للاسترداد. قد يخزن Policy للترخيص في التطبيق مؤقتًا نتيجة الفحص الأولي للترخيص ولا يحتاج إلى إعادة التحقق من الترخيص حتى تنتهي مدة الصلاحية.
  • عندما لا يمكن استرداد المبلغ المدفوع في التطبيق، يحدد الخادم فترة صلاحية أطول، تكون عادةً عددًا من الأيام.
  • بالنسبة إلى أي تطبيق مجاني، يضبط الخادم مدة الصلاحية على قيمة عالية جدًا (long.MAX_VALUE). وهذا يضمن أنه شريطة أن يخزّن Policy الطابع الزمني للصلاحية مؤقتًا محليًا، لن يحتاج إلى إعادة التحقق من حالة ترخيص التطبيق في المستقبل.

في عملية تنفيذ ServerManagedPolicy، يتم استخدام الطابع الزمني المستخرَج (mValidityTimestamp) كشرط أساسي لتحديد ما إذا كان يجب إعادة التحقّق من حالة الترخيص مع الخادم قبل السماح للمستخدم بالوصول إلى التطبيق.

فترة إعادة المحاولة والحد الأقصى لعدد إعادة المحاولة

في بعض الحالات، قد تمنع شروط النظام أو الشبكة فحص ترخيص التطبيق من الوصول إلى خادم الترخيص أو تمنع استجابة الخادم من الوصول إلى تطبيق عميل Google Play. على سبيل المثال، قد يشغِّل المستخدم تطبيقًا في حال عدم توفّر شبكة خلوية أو اتصال بيانات، كما هو الحال عند التواجد على متن طائرة، أو عندما يكون اتصال الشبكة غير مستقر أو عندما تكون إشارة شبكة الجوّال ضعيفة.

عندما تمنع مشاكل في الشبكة فحص الترخيص أو تقاطعه، يرسل برنامج Google Play إشعارًا إلى التطبيق من خلال عرض رمز استجابة RETRY لطريقة processServerResponse() في Policy. في حال حدوث مشاكل في النظام، مثلاً عندما يتعذّر على التطبيق الربط بتطبيق ILicensingService في Google Play، تطلب مكتبة LicenseChecker نفسها من طريقة السياسة processServerResponse() باستخدام رمز الاستجابة RETRY.

وبشكل عام، يشير رمز الاستجابة RETRY إلى التطبيق بحدوث خطأ، ما أدى إلى منع اكتمال عملية التحقّق من الترخيص.

يساعد خادم Google Play أحد التطبيقات في إدارة الترخيص في ظل شروط الخطأ من خلال ضبط "فترة السماح" لإعادة المحاولة والحد الأقصى لعدد المحاولات المسموح بها. يضمِّن الخادم هذه القيم في جميع استجابات فحص الترخيص، وإلحاقها كقيم إضافية ضمن المفتاحين GT وGR.

يمكن للتطبيق Policy استخراج الإضافة GT وGR واستخدامها للسماح بالوصول إلى التطبيق بشكل مشروط، على النحو التالي:

  • بالنسبة إلى عملية التحقّق من الترخيص التي تؤدي إلى ظهور استجابة RETRY، يجب أن تخزن علامة Policy مؤقتًا رمز الاستجابة RETRY وأن تزيد من عدد ردود RETRY.
  • من المفترض أن تسمح Policy للمستخدم بالوصول إلى التطبيق، بشرط أن لا تزال فترة السماح لإعادة المحاولة نشطة أو لم يتم الوصول إلى الحد الأقصى لعدد عمليات إعادة المحاولة.

وتستخدم السمة ServerManagedPolicy قيم GT وGR التي يوفّرها الخادم كما هو موضّح أعلاه. يوضّح المثال أدناه المعالجة المشروطة لردود إعادة المحاولة في طريقة allow(). يتم الاحتفاظ بعدد RETRY من الردود في طريقة processServerResponse()، ولا يتم عرضه.

Kotlin

fun allowAccess(): Boolean {
    val ts = System.currentTimeMillis()
    return when(lastResponse) {
        LICENSED -> {
            // Check if the LICENSED response occurred within the validity timeout.
            ts <= validityTimestamp  // Cached LICENSED response is still valid.
        }
        RETRY -> {
            ts < lastResponseTime + MILLIS_PER_MINUTE &&
                    // Only allow access if we are within the retry period
                    // or we haven't used up our max retries.
                    (ts <= retryUntil || retryCount <= maxRetries)
        }
        else -> false
    }
}

Java

public boolean allowAccess() {
    long ts = System.currentTimeMillis();
    if (lastResponse == LicenseResponse.LICENSED) {
        // Check if the LICENSED response occurred within the validity timeout.
        if (ts <= validityTimestamp) {
            // Cached LICENSED response is still valid.
            return true;
        }
    } else if (lastResponse == LicenseResponse.RETRY &&
                ts < lastResponseTime + MILLIS_PER_MINUTE) {
        // Only allow access if we are within the retry period
        // or we haven't used up our max retries.
        return (ts <= retryUntil || retryCount <= maxRetries);
    }
    return false;
}