بالإضافة إلى قواعد الحفظ العامة وأنواع قواعد الحفظ الإضافية والخيارات العامة، يمكنك استخدام قواعد معيّنة لتحديد المشاكل وحلّها في عملية التحسين.
-checkdiscard
تتيح لك القاعدة -checkdiscard التحقّق مما إذا كان R8 قد تجاهل بنجاح فئة أو عنصرًا من عناصرها كنت تتوقّع إزالته. إذا لم يتم تجاهل الفئة أو العنصر المحدّدَين، سيتعذّر إنشاء التطبيق.
صيغة -checkdiscard هي كما يلي:
-checkdiscard <class_specification>
في المثال التالي، يتعذّر إنشاء التطبيق إذا تم الاحتفاظ بالحقل userId أو الطريقة setLabel() من الفئة com.example.models.User:
-checkdiscard class com.example.models.User{
private java.lang.String userId;
public void setLabel(java.lang.String);
}
قد يظل رمز الصف الدراسي متوفّرًا في التطبيق إذا تم تضمين طُرق الصف الدراسي في صفوف أخرى. للتأكّد من أنّه تمت إزالة الرمز بالكامل وليس فقط تضمينه، أضِف قاعدة مقابلة تمنع R8 من إجراء عمليات التحسين على الفئة المستهدَفة، وذلك من خلال الجمع بين -checkdiscard وقاعدة -keep,allowshrinking. ويحظر ذلك إجراء تحسينات مثل دمج الفئات وتضمينها. إذا تم استيفاء قاعدة -checkdiscard، لن يتضمّن التطبيق المحسَّن أي محتوى من الفئات المطابِقة.
يوضّح المثال التالي طريقة الاستخدام هذه:
# Either keep or remove the class, don't rename or otherwise optimize it
-keep,allowshrinking class com.example.foo { *; }
# Verify that the class and all of its fields and methods are removed.
-checkdiscard class com.example.foo
-whyareyoukeeping
استخدِم قاعدة -whyareyoukeeping لتحديد سبب احتفاظ R8 بفئة أو حقل أو طريقة معيّنة في إصدار تطبيقك. يمكن الاحتفاظ بأحد العناصر لعدة أسباب، ولكن هذه القاعدة لا تقدّم سوى السبب الذي يوضّح أقصر مسار إلى العنصر من عنصر تم الاحتفاظ به. إذا أزلت هذا المسار من الرمز، قد يظل العنصر محتفظًا به ولكن لسبب مختلف.
في ما يلي الأسباب المحتمَلة:
قاعدة الاحتفاظ: يمكن أن تكون قاعدة الاحتفاظ من التطبيق أو من مكتبة مستخدَمة أو من قواعد تم إنشاؤها بواسطة أداة AAPT (أداة حزم أصول Android).
المراجع المتعدية من الرموز أو الموارد المحفوظة: إذا احتفظ R8 بالرموز أو XML (مثل التصاميم)، سيتم الاحتفاظ بأي شيء يشير إليه بشكل ثابت.
بناء الجملة هو:
-whyareyoukeeping <class_specification>
مثلاً:
-whyareyoukeeping class com.example.foo.MainActivity {
private void setLabel(...);
}
تتم طباعة الناتج في وحدة التحكّم.
إذا لم تكن لديك أي قاعدة تحتفظ بـ setLabel()، ستكون النتيجة كما يلي:
com.example.foo.MainActivity
|- is referenced in keep rule:
| /app/build/intermediates/aapt_proguard_file/release/processReleaseResources/aapt_rules.txt:4:1
Nothing is keeping void com.example.foo.MainActivity.setLabel()
إذا كانت لديك قاعدة الاحتفاظ بالبيانات تستهدف setLabel()، ستكون النتيجة مشابهة لما يلي:
com.example.foo.MainActivity
|- is referenced in keep rule:
| /app/proguard-rules.pro:23:1
void com.example.foo.MainActivity.setLabel()
|- is referenced in keep rule:
| /app/proguard-rules.pro:23:1