ProGuard — คืออะไร, ความสามารถและการตั้งค่าการทำให้โค้ดสับสน

ผู้แต่ง: IT Sectr เผยแพร่เมื่อ: 2026-04-03 เวลาอ่าน: 8 นาที

ProGuard — เครื่องมือสำหรับการบีบอัด เพิ่มประสิทธิภาพ และทำให้ Java bytecode สับสน ซึ่งถูกรวมอยู่ใน Android SDK เพื่อป้องกันแอปพลิเคชันจากการ reverse-engineering ตามข้อมูลจาก Google I/O Security Session (2025), การตั้งค่า ProGuard ที่ถูกต้อง ช่วยลดขนาด APK ได้ 15-25% และลดความเสี่ยงในการรั่วไหลของโค้ดลง 60% เครื่องมือนี้กลายเป็นมาตรฐานสำหรับการพัฒนา Android และถูกใช้ในแอปพลิเคชันนับล้านทั่วโลก

สาระสำคัญ

  • ProGuard — เครื่องมือสำหรับการบีบอัด เพิ่มประสิทธิภาพ และทำให้ Java bytecode สับสนในแอปพลิเคชัน Android
  • การบีบอัด ลบคลาส เมธอด และฟิลด์ที่ไม่ได้ใช้งาน ทำให้ขนาด APK เล็กลง
  • การทำให้สับสน เปลี่ยนชื่อตัวระบุเป็นชื่อสั้นที่ไม่มีความหมายเพื่อป้องกันการ decompile
  • การเพิ่มประสิทธิภาพ ทำการ inline เมธอดและทำให้โค้ดง่ายขึ้นในระดับ bytecode
  • ไฟล์ Mapping ช่วยให้ deobfuscate รายงาน crash และจำเป็นสำหรับการสนับสนุนบิลด์แบบ release

ProGuard คืออะไร?

ProGuard — เครื่องมือที่เผยแพร่แบบฟรีสำหรับการประมวลผล Java bytecode พัฒนาโดยบริษัท Guardsquare มันถูกรวมอยู่ใน Android SDK และทำหน้าที่สำคัญสามประการ: การบีบอัด (shrinking) การเพิ่มประสิทธิภาพ (optimization) และการทำให้โค้ดสับสน (obfuscation) ProGuard วิเคราะห์ bytecode ทั้งหมดของแอปพลิเคชันและ dependencies ของมัน ระบุคลาสและเมธอดที่ไม่ได้ใช้งาน ลบทิ้ง จากนั้น ทำให้สับสน โค้ดที่เหลือ

ประวัติและตำแหน่ง

ProGuard ถูกสร้างโดย Eric Lafarge ในปี 2000 โดยเป็นเครื่องมือเพิ่มประสิทธิภาพสำหรับแอปพลิเคชัน Java เมื่อ Android ปรากฏในปี 2008 ProGuard ถูกรวมเข้ากับ Android SDK และกลายเป็นเครื่องมือมาตรฐานสำหรับการป้องกันแอปพลิเคชัน ตามสถิติของ Guardsquare (2024), ProGuard ถูกใช้ใน มากกว่า 80% ของแอปพลิเคชันจาก Google Play รวมถึงแอปพลิเคชันของธนาคารขนาดใหญ่และบริษัทเทคโนโลยี

ProGuard ประมวลผลโค้ดอย่างไร

ProGuard ดำเนินการประมวลผลในสี่ขั้นตอน ในขั้นตอนแรก (shrink) เครื่องมือจะวิเคราะห์จุดเข้าใช้งานของแอปพลิเคชันและระบุว่าคลาส เมธอด และฟิลด์ใดบ้างที่สามารถเข้าถึงได้ระหว่างการทำงาน ในขั้นตอนที่สอง (optimize) ProGuard จะแปลง bytecode เพื่อเพิ่มประสิทธิภาพการทำงาน ขั้นตอนที่สาม (obfuscate) จะเปลี่ยนชื่อตัวระบุ ในขั้นตอนสุดท้าย preverify จะเพิ่ม metadata ที่จำเป็นสำหรับการตรวจสอบ bytecode บนเครื่องเสมือน

ความสามารถหลักของ ProGuard

มาดูรายละเอียดแต่ละฟังก์ชันหลักทั้งสามของ ProGuard กัน: การบีบอัด การเพิ่มประสิทธิภาพ และการทำให้โค้ดสับสน การเข้าใจกลไกแต่ละอย่างจะช่วยให้ตั้งค่าเครื่องมือได้อย่างเหมาะสมที่สุด

การบีบอัดโค้ด (Shrinking)

ProGuard วิเคราะห์กราฟการเรียกจากจุดเข้าใช้งาน (main-method, Activity, BroadcastReceiver) และลบโค้ดที่ไม่ได้ใช้งาน ในโปรเจกต์ Android ทั่วไปที่มีไลบรารีอย่าง Retrofit, OkHttp และ Gson การบีบอัดสามารถลบ bytecode ได้ถึง 40% รวมถึงเมธอดของไลบรารีที่ไม่ได้ใช้งาน โค้ด debug และคลาสทดสอบ ซึ่งช่วยลดขนาด APK และลดเวลาในการโหลดแอปพลิเคชันโดยตรง

การเพิ่มประสิทธิภาพ (Optimization)

ในขั้นตอน การเพิ่มประสิทธิภาพ ProGuard ดำเนินการแปลง bytecode มากกว่า 20 รูปแบบ: การ inline เมธอดสั้น ๆ การลบพารามิเตอร์ที่ไม่ได้ใช้งาน การทำให้ expressions ทางตรรกะง่ายขึ้น การรวมบล็อกโค้ดที่เหมือนกัน ตัวอย่างเช่น getter และ setter สั้น ๆ สามารถถูกแทนที่ด้วยการเข้าถึงฟิลด์โดยตรง การเพิ่มประสิทธิภาพสามารถเร่งความเร็วการทำงานของโค้ดได้ 5-15% ขึ้นอยู่กับโครงสร้างของแอปพลิเคชัน

การทำให้โค้ดสับสน (Obfuscation)

การทำให้โค้ดสับสน ใน ProGuard ทำงานโดยการเปลี่ยนชื่อคลาส เมธอด และฟิลด์เป็นลำดับตัวอักษรสั้น ๆ: a, b, c, a.a, a.b และอื่น ๆ การอ้างอิงทั้งหมดไปยังองค์ประกอบที่ถูกเปลี่ยนชื่อจะถูกอัปเดตโดยอัตโนมัติทั่วทั้งโค้ด สิ่งสำคัญที่ต้องทราบคือ การทำให้โค้ดสับสนไม่ได้เปลี่ยนพฤติกรรมของโปรแกรม แต่เพียงทำให้ การเข้าใจ โค้ดที่ถูก decompile ยากขึ้นเท่านั้น ไลบรารีและ API สาธารณะควรถูกแยกออกจากการทำให้โค้ดสับสนผ่านกฎ keep

java
// ก่อนการใช้ ProGuard
public class LoginManager {
    public User authenticateUser(String username, String password) {
        // ตรรกะการตรวจสอบสิทธิ์
    }
}

// หลังการใช้ ProGuard
public class a {
    public Object a(String b, String c) {
        // ตรรกะเดียวกันกับชื่อที่ถูกเปลี่ยนใหม่
    }
}

การตั้งค่า ProGuard ในโปรเจกต์ Android

การกำหนดค่า ProGuard — เป็นขั้นตอนสำคัญในการตั้งค่าบิลด์ของแอปพลิเคชัน Android กฎที่ไม่ถูกต้องอาจนำไปสู่การลบคลาสที่จำเป็น และส่งผลให้เกิด crash ในเวอร์ชัน release

การตั้งค่าพื้นฐานใน build.gradle

การเปิดใช้งาน ProGuard ในโปรเจกต์ Android รวมถึงการตั้งค่า flag minifyEnabled เป็น true สำหรับบิลด์ประเภท release กฎมาตรฐานของ ProGuard มาพร้อมกับ Android SDK ในไฟล์ proguard-android-optimize.txt กฎที่ผู้ใช้กำหนดจะถูกเพิ่มในไฟล์แยกต่างหาก proguard-rules.pro เมื่อบิลด์ ProGuard จะใช้กฎมาตรฐานก่อน จากนั้นจึงใช้กฎที่ผู้ใช้กำหนด ซึ่งช่วยให้ แทนที่ การกำหนดค่าพื้นฐานได้

groovy
android {
    buildTypes {
        release {
            minifyEnabled true
            proguardFiles getDefaultProguardFile(
                'proguard-android-optimize.txt'
            ), 'proguard-rules.pro'
        }
    }
}

ไฟล์ proguard-rules.pro

ไฟล์ กฎ ที่ผู้ใช้กำหนดประกอบด้วยคำสั่งเฉพาะสำหรับโปรเจกต์นั้น ๆ กฎทั่วไปรวมถึงการเก็บคลาสที่ใช้ผ่าน reflection โมเดลข้อมูลสำหรับ serialization แบบ Gson/Moshi อินเทอร์เฟซ callback ของไลบรารี และคลาสที่มี annotation เฉพาะ แต่ละคำสั่งเริ่มต้นด้วยคีย์เวิร์ด -keep, -dontwarn หรือ -keepclassmembers และกำหนด รูปแบบ ของคลาสที่ ProGuard ไม่ควรเปลี่ยนแปลง

properties
# เก็บโมเดลข้อมูลสำหรับ Gson
-keep class com.example.data.model.** { *; }

# เก็บคลาสที่ใช้ผ่าน reflection
-keep class * implements com.google.gson.TypeAdapterFactory

# ไม่สนใจคำเตือนของไลบรารี
-dontwarn okhttp3.internal.**
-dontwarn retrofit2.**

# เก็บ enum (ลักษณะเฉพาะของ ProGuard)
-keep class * extends java.lang.Enum { *; }

กฎของ ProGuard: keep, dontwarn และอื่น ๆ

ไวยากรณ์การกำหนดค่า ProGuard รวมถึงคำสั่งหลายหมวดหมู่ ซึ่งแต่ละหมวดหมู่ควบคุมลักษณะเฉพาะของการประมวลผล มาดูคำสั่งหลักที่จำเป็นสำหรับการตั้งค่าที่ถูกต้องกัน

คำสั่งวัตถุประสงค์ตัวอย่าง
-keepเก็บคลาสและสมาชิกทั้งหมดไว้-keep class com.example.MyClass
-keepclassmembersเก็บเฉพาะสมาชิกของคลาส-keepclassmembers class * { @Inject *; }
-dontwarnไม่สนใจคำเตือน-dontwarn okhttp3.internal.**
-keepparameternamesเก็บชื่อพารามิเตอร์ของเมธอด-keepparameternames
-keepattributesเก็บ attributes (annotations, EnclosingMethod)-keepattributes *Annotation*
-dontoptimizeปิดการเพิ่มประสิทธิภาพ-dontoptimize

Reflection และการโหลดแบบไดนามิก

ProGuard ไม่สามารถวิเคราะห์โค้ดที่โหลดผ่าน reflection (Class.forName()), ServiceLoader หรือการโหลด DEX-ไฟล์แบบไดนามิกได้ในเชิงสถิติ หากคลาสถูกสร้างขึ้นโดยใช้ชื่อในรูปแบบสตริง ProGuard จะไม่รู้ถึงการมีอยู่ของมันและอาจลบทิ้งเป็นโค้ดที่ไม่ได้ใช้งาน คลาสทั้งหมดดังกล่าวต้องถูกเก็บไว้อย่างชัดเจนผ่าน -keep นี่เป็น สาเหตุ ที่พบบ่อยที่สุดของ crash ในบิลด์ release หลังจากเปิดใช้ ProGuard

ไลบรารีและ AAR-dependencies

ไลบรารีมักรวม กฎ ProGuard ของตัวเอง ซึ่งถูกเพิ่มโดยอัตโนมัติในบิลด์ผ่าน consumer-rules.pro ที่ฝังอยู่ในไฟล์ AAR Android Gradle Plugin จะใช้กฎเหล่านี้โดยอัตโนมัติเมื่อบิลด์ นักพัฒนาเพียงแค่ต้องตรวจสอบว่าไลบรารีทั้งหมดที่ใช้ให้กฎที่ถูกต้อง และเพิ่มเติมในโปรเจกต์หากจำเป็น

การดีบักปัญหา ProGuard

เมื่อเกิดข้อผิดพลาดหลังจากเปิดใช้ ProGuard ให้ใช้ไฟล์ mapping สำหรับ deobfuscate stack trace สำหรับการวินิจฉัย ให้ใช้คีย์ -whyareyoukeeping ซึ่งแสดงสาเหตุที่เก็บคลาสไว้ในบิลด์ผลลัพธ์ การปิด -optimizationpasses และ -obfuscation ชั่วคราวช่วยระบุตำแหน่งของปัญหา ตามข้อมูลของ Guardsquare, 80% ของปัญหากับ ProGuard แก้ไขได้โดยการเพิ่มกฎ -keep สำหรับคลาสที่ใช้ reflection

ProGuard และ R8: การเปรียบเทียบและการย้ายไปใช้

เมื่อ Android Gradle Plugin 3.4 (2019) เปิดตัว Google ได้นำเสนอ R8 — ผู้สืบทอดของ ProGuard ที่ถูกรวมเข้ากับคอมไพเลอร์ D8/R8 โดยตรง ภายในปี 2023 R8 ได้แทนที่ ProGuard อย่างสมบูรณ์ใน AGP 8.0 แต่การเข้าใจความแตกต่างทางสถาปัตยกรรมเป็นสิ่งสำคัญสำหรับการย้ายโปรเจกต์

ความแตกต่างทางสถาปัตยกรรม

ProGuard ทำงานเป็นเครื่องมือแยกต่างหาก โดยประมวลผล Java bytecode (ไฟล์ .class) ก่อนการแปลงเป็น DEX ส่วน R8 ถูกรวมเข้ากับคอมไพเลอร์ DEX และประมวลผลโค้ดในระดับที่ต่ำกว่า ซึ่งช่วยให้ดำเนินการ เพิ่มประสิทธิภาพ ที่ ProGuard ไม่สามารถทำได้ R8 ยังรองรับ desugaring — การแปลง syntactic sugar ของ Java 8+ เป็นโค้ดที่เข้ากันได้กับ API ระดับเก่าของ Android

ข้อดีของ R8

ตามข้อมูลของ Google Android Performance Team (2025), R8 ให้การบีบอัดโค้ดที่ดีกว่า 10-15% เมื่อเทียบกับ ProGuard ภายใต้กฎเดียวกัน R8 เร็วกว่า — เวลาบิลด์ลดลง 20-30% นอกจากนี้ R8 ยังลบ dead code ได้มากกว่าเนื่องจากการวิเคราะห์ในระดับ DEX แทนที่จะเป็น class-ไฟล์ R8 เข้ากันได้อย่างสมบูรณ์กับไวยากรณ์กฎของ ProGuard ซึ่งทำให้การย้าย โปร่งใส สำหรับนักพัฒนา

กระบวนการย้ายไปใช้

การเปลี่ยนจาก ProGuard เป็น R8 นั้นง่าย: ใน AGP 8.0+ R8 ถูกใช้โดยค่าเริ่มต้น สำหรับโปรเจกต์เก่า ต้องลบ ProGuard ออกจาก classpath และอัปเดต gradle.properties: android.enableR8=true กฎของ ProGuard เข้ากันได้กับ R8 โดยไม่ต้องเปลี่ยนแปลงในกรณีส่วนใหญ่ ขอแนะนำให้ทดสอบบิลด์ release บน อุปกรณ์เป้าหมาย ทั้งหมดหลังจากเปลี่ยน เนื่องจาก R8 อาจลบโค้ดที่ ProGuard เคยเก็บไว้

คำถามที่พบบ่อย

ทำไมแอปพลิเคชันถึง crash หลังจากเปิดใช้ ProGuard?

สาเหตุที่พบบ่อยที่สุดคือ การลบคลาส ที่ใช้ผ่าน reflection, serialization แบบ Gson/Moshi หรือไลบรารีที่มีการโหลด DEX-ไฟล์แบบไดนามิก วิธีแก้ไข: เพิ่มกฎ -keep สำหรับคลาสทั้งหมดที่สร้างผ่าน Class.forName(), implements Parcelable, serialization ผ่าน JSON หรือมี annotation @Inject ใช้ไฟล์ mapping สำหรับ deobfuscate stack trace และระบุคลาสที่ถูกลบออกจากบิลด์

จะอ่านไฟล์ mapping ของ ProGuard อย่างถูกต้องได้อย่างไร?

ไฟล์ mapping อยู่ใน build/outputs/mapping/release/mapping.txt หลังจากบิลด์ รูปแบบ: ชื่อ_ดั้งเดิม -> ชื่อ_ที่ถูกทำให้สับสน -> ประเภท Android Studio รองรับ deobfuscation ผ่าน Build > Analyze APK: อัปโหลด APK วาง stack trace และรับชื่อคลาสที่อ่านได้ สำหรับ CI/CD ให้เก็บไฟล์ mapping สำหรับแต่ละเวอร์ชันใน repository แยกต่างหาก หรือที่เก็บข้อมูลบนคลาวด์

จำเป็นต้องปิด ProGuard เมื่อดีบักบิลด์ debug หรือไม่?

ใช่ ควรเปิด ProGuard เฉพาะสำหรับบิลด์ release เท่านั้น บิลด์ debug ใช้ minifyEnabled false ซึ่งช่วยให้คอมไพล์เร็วขึ้นและเก็บชื่อคลาสที่อ่านได้สำหรับดีบักเกอร์ ในโหมด debug การทำให้โค้ดสับสนจะขัดขวางการดีบักและการดำเนินการทีละขั้นตอน ในขณะที่การบีบอัดจะทำให้ iteration ช้าลง สำหรับการทดสอบความถูกต้องของการทำให้โค้ดสับสน ให้ใช้ บิลด์ release บนอุปกรณ์จริง

จะจัดการกับคำเตือนและข้อผิดพลาดของ ProGuard อย่างไร?

คำเตือน ProGuard (WARNING) บ่งชี้ถึงปัญหาที่ไม่ทำให้บิลด์หยุด แต่สามารถบ่งชี้ถึงข้อผิดพลาดที่อาจเกิดขึ้นระหว่างการทำงานได้ หากคำเตือนไม่ทำให้เกิด crash ให้เพิ่ม -dontwarn สำหรับไลบรารีนั้น หากคำเตือนเกี่ยวข้องกับคลาสที่หายไปซึ่งไม่ได้ใช้ในแอปพลิเคชัน ก็ให้ใช้ -dontwarn เช่นกัน การไม่สนใจคำเตือนทั้งหมดโดยไม่พิจารณา ไม่แนะนำ

ProGuard แตกต่างจาก DexGuard สำหรับ Android อย่างไร?

ProGuard — เครื่องมือฟรีที่มีฟังก์ชันพื้นฐาน: การบีบอัด การเพิ่มประสิทธิภาพ การเปลี่ยนชื่อคลาสและเมธอด DexGuard — ผลิตภัณฑ์เชิงพาณิชย์จาก Guardsquare เดียวกัน ซึ่งเพิ่มการทำให้ control flow สับสน การเข้ารหัสสตริงและทรัพยากร การป้องกันการดีบัก และการทำให้ทรัพยากรสับสน DexGuard ถูกใช้ในแอปพลิเคชัน ธนาคาร และเกมที่มีข้อกำหนดการป้องกันสูง

สรุป

  • ProGuard — เครื่องมือมาตรฐานสำหรับการบีบอัด เพิ่มประสิทธิภาพ และทำให้โค้ดสับสนสำหรับแอปพลิเคชัน Android
  • การบีบอัด ลบ bytecode ที่ไม่ได้ใช้งานได้ถึง 40% ซึ่งช่วยลดขนาด APK สุดท้ายได้อย่างมาก
  • การทำให้โค้ดสับสน เปลี่ยนชื่อคลาสและเมธอด ป้องกันการ decompile
  • กฎ keep จำเป็นสำหรับคลาสที่ใช้ผ่าน reflection และ serialization
  • ไฟล์ mapping จำเป็นสำหรับ deobfuscate รายงาน crash ในบิลด์ release ของแอปพลิเคชัน
  • R8 แทนที่ ProGuard ใน AGP 8.0 โดยให้การบีบอัดโค้ดที่ดีกว่าและความเร็วบิลด์ที่สูงกว่า
  • การทดสอบ บิลด์ release ด้วย ProGuard บนอุปกรณ์จริงเป็นสิ่งจำเป็นก่อนเผยแพร่ในร้านค้า

เราจะพัฒนาแอปพลิเคชันบนมือถือแบบครบวงจร

IT Sectr สร้างแอปพลิเคชัน iOS และ Android สำหรับสตาร์ทอัพและธุรกิจตั้งแต่ปี 2017 เราจะให้คำแนะนำและเสนอวิธีแก้ปัญหาที่ดีที่สุดแก่คุณ

ปรึกษาโครงการ

อ่านเพิ่มเติม