ประเด็นด้านความปลอดภัยกับ Recents Screen บนแอนดรอยด์

เวลาที่ผู้ใช้กดออกจากแอปของนักพัฒนา ระบบแอนดรอยด์จะเก็บภาพล่าสุดจากแอปนั้น ๆ เพื่อแสดงให้ผู้ใช้เห็นใน Recents Screen อยู่เสมอ เพื่อให้ผู้ใช้สามารถกลับมาใช้งานแอปต่อได้ง่าย สามารถรู้ได้ว่าเคยเปิดหน้าไหนในแอปทิ้งไว้

สำหรับแอปทั่วไปอาจจะไม่ต้องกังวลเกี่ยวกับการแสดงภาพดังกล่าวใน Recents Screen มากนัก แต่สำหรับแอปที่ต้องการความปลอดภัยสูง การแสดงภาพใน Recents Screen มีโอกาสที่จะเป็นช่องโหว่สำหรับผู้ที่ประสงค์ร้ายก็เป็นได้ ถ้าภาพดังกล่าวมีการแสดงข้อมูลที่เป็นความลับของผู้ใช้

แอปเหล่านี้มักจะออกแบบให้ผู้ใช้ต้องล็อกอินใหม่เมื่อกลับเข้ามาใช้งานแอปหลังจากที่ออกไปแล้วซักพัก แต่ผู้ที่ประสงค์ร้ายก็อาจจะเห็นข้อมูลจากภาพที่แสดงใน Recents Screen ได้โดยไม่ต้องเข้าใช้งานแอปนั้น ๆ

เพื่อป้องกันปัญหาดังกล่าว ระบบแอนดรอยด์จึงมีคำสั่งให้นักพัฒนากำหนดได้ว่าจะให้ Activity ใด ๆ ไม่แสดงภาพบน Recents Screen

// Activity
override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    window.addFlags(WindowManager.LayoutParams.FLAG_SECURE)
    setContentView(/* ... */)
}

เมื่อผู้ใช้ออกจากแอปในระหว่างที่ Activity กำลังแสดงผลอยู่ ภาพที่เห็นใน Recents Screen จะกลายเป็นภาพสีขาวทั้งหมดแทน ซึ่งจะช่วยซ่อนข้อมูลในแอปเมื่อกดดูผ่าน Recents Screen นั่นเอง

การกำหนดค่า WindowManager.LayoutParams.FLAG_SECURE จะมีผลเฉพาะ Activity ที่กำหนดค่าเท่านั้น ดังนั้นถ้ามีการเปลี่ยนไปยัง Activity ตัวอื่น ๆ ก็จะไม่มีผล จึงทำให้นักพัฒนาสามารถกำหนดค่าดังกล่าวแยกระหว่างแต่ละ Activity ได้อย่างอิสระ

และนอกจากนี้การใช้คำสั่งดังกล่าวจะทำให้ผู้ใช้บันทึกภาพหน้าจอ (Screen Capture หรือ Screen Recording) ไม่ได้ด้วยเช่นกัน โดยระบบแอนดรอยด์อาจจะขึ้นแจ้งเตือนว่าไม่ให้บันทึกภาพหน้าจอ หรือได้เป็นภาพสีดำ ซึ่งจะขึ้นอยู่กับแต่ละยี่ห้อและเวอร์ชันของแอนดรอยด์

การซ่อนภาพจาก Recents Screen กับห้ามบันทึกภาพนั้นเป็นของคู่กัน

เพราะจุดประสงค์หลักของ WindowManager.LayoutParams.FLAG_SECURE คือการป้องกันการบันทึกภาพจากระบบแอนดรอยด์ ดังนั้นการใช้ Flag ดังกล่าวจะทำให้ภาพของ Activity ถูกซ่อนจาก Recents Screen และป้องกันการบันทึกภาพหน้าจอเสมอ

นั่นจึงทำให้มีปัญหากับบางแอปที่ต้องการซ่อนภาพใน Recents Screen แต่อยากจะให้บันทึกภาพหน้าจอได้อยู่ หรือจะเรียกว่าเป็นข้อจำกัดของระบบแอนดรอยด์ก็ว่าได้ เพราะต่างจาก iOS ที่สามารถกำหนดการทำงานของทั้ง 2 อย่างนี้แยกกันได้

ทางเลือกสำหรับนักพัฒนาที่อยากให้บันทึกภาพจากในแอปได้

ในกรณีที่แอปจำเป็นต้องซ่อนภาพใน Recents Screen และต้องการให้ผู้ใช้สามารถบันทึกภาพจากในแอปได้ เจ้าของบล็อกแนะนำว่าทำให้แอปบันทึกภาพจากในแอปผ่านโค้ดแทน (แปลง UI ที่แสดงในแอปให้กลายเป็น Bitmap แล้วบันทึกเป็นไฟล์ภาพลงในเครื่อง)

Screen Capture หรือ Capture ภาพบน View ผ่านโค้ด
วันนี้ขอหยิบเรื่องราวของการใช้คำสั่งเพื่อบันทึกภาพหน้าจอภายในแอปมาเล่าสู่กันฟังฮะ

แน่นอนว่าวิธีดังกล่าว ผู้ใช้จะไม่สามารถกดปุ่ม Screen Capture ของระบบแอนดรอยด์ได้อยู่ดี เพราะเป็นการเรียกคำสั่งจากภายในแอปโดยตรง ดังนั้นควรออกแบบ UI เพื่อให้ผู้ใช้รับรู้ได้ว่าจะต้องบันทึกภาพหน้าจอผ่านแอปแทน (อาจจะสร้างปุ่มสำหรับกดเพื่อบันทึกภาพ)