การเพิ่มความปลอดภัยของเสียงเบื้องหลัง

ตั้งแต่ Android 17 เป็นต้นไป เฟรมเวิร์กเสียงจะบังคับใช้ข้อจำกัดในการโต้ตอบเสียงในเบื้องหลัง ซึ่งรวมถึงการเล่นเสียง คำขอโฟกัสเสียง และ API การเปลี่ยนระดับเสียง เพื่อให้มั่นใจว่าผู้ใช้เป็นผู้เริ่มการเปลี่ยนแปลงเหล่านี้โดยเจตนา

หากนักพัฒนาแอปต้องการควบคุมเสียงโดยไม่มีกิจกรรมที่มองเห็นได้ นักพัฒนาแอป ควรตรวจสอบว่าแอปมีบริการที่ทำงานอยู่เบื้องหน้า (ซึ่งไม่ใช่ประเภท SHORT_SERVICE) ที่เริ่มต้นด้วยความสามารถขณะใช้งาน (WIU) ระบบจะให้ความสามารถ WIU แก่ บริการที่ทำงานอยู่เบื้องหน้าหากบริการนั้นเริ่มต้นขึ้นเพื่อตอบสนองต่อ MediaSessionEvent หรือขณะที่แอปแสดงต่อผู้ใช้

หากแอปพยายามเรียกใช้ Audio API ขณะที่แอปไม่ได้อยู่ในวงจรที่ถูกต้อง API การเล่นเสียงและการเปลี่ยนระดับเสียงจะทำงานไม่สำเร็จโดยไม่มีการแจ้งเตือน ข้อยกเว้นหรือแสดงข้อความว่าไม่สำเร็จ API โฟกัสเสียงล้มเหลวโดยมีรหัสผลลัพธ์ AUDIOFOCUS_REQUEST_FAILED

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

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

เราขอแนะนำให้นักพัฒนาแอปทดสอบแอปของตนและแสดงความคิดเห็นเกี่ยวกับการเปลี่ยนแปลงลักษณะการทำงาน หากมี Use Case ของเสียงที่ตั้งใจไว้ซึ่งได้รับผลกระทบในทางลบ โปรดรายงานปัญหาโดยใช้เครื่องมือติดตามปัญหาความเข้ากันได้ของแอป Android 17นี้

ระบุกรณีการใช้งานเสียงพื้นหลังที่ได้รับผลกระทบ

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

หากแอปของคุณมีเจตนาที่จะเล่นเสียงหรือใช้ API เสียงขณะแสดงกิจกรรมที่ผู้ใช้มองเห็น รวมถึงการใช้โหมดภาพในภาพ (PiP) การเปลี่ยนแปลงเหล่านี้จะไม่ส่งผลต่อแอป

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

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

สถานการณ์เสียงพื้นหลังที่อาจได้รับผลกระทบ

หากแอปไม่ปฏิบัติตามรูปแบบของการโต้ตอบด้วยเสียงอย่างต่อเนื่อง ซึ่งเริ่มต้นขณะที่แอปเปิดอยู่ หรือเป็นการตอบสนองต่อทริกเกอร์ที่ผู้ใช้ระบุอย่างชัดเจน ระบบอาจระงับฟังก์ชันการทำงานของแอปโดยไม่แจ้งให้ทราบ

ตัวอย่างเช่น หากแอปของคุณเริ่มบริการที่ทำงานอยู่เบื้องหน้าเพื่อตอบสนองต่อ BOOT_COMPLETE และพยายามโต้ตอบกับเสียง ระบบจะระงับแอป

แนวทางปฏิบัติแนะนำเกี่ยวกับเสียงพื้นหลังเพื่อลดผลกระทบ

  • ใช้คอมโพเนนต์ MediaSessionService ของไลบรารี Jetpack media3 เพื่อ จัดการการเล่นเสียงในเบื้องหลัง

    หากทำเช่นนั้น แอปของคุณจะไม่ได้รับผลกระทบจากการเพิ่มความปลอดภัยในเบื้องหลังเนื่องจากไลบรารีจะช่วยจัดการวงจรการเล่น

  • หากไม่ได้ใช้ประโยชน์จากไลบรารี Media3 คุณจะต้องเริ่ม mediaPlayback FGS ด้วยตนเอง เริ่มต้นบริการที่ทำงานอยู่เบื้องหน้าเสมอในขณะที่แอปทำงานอยู่เบื้องหน้าหากอาจมีเสียงเบื้องหลัง

    เช่น หากแอปของคุณเป็นแอปสตรีมมิงวิดีโอซึ่งโดยปกติแล้วจะ ทำงานอยู่เบื้องหน้าเท่านั้น แต่มีฟีเจอร์ที่ให้ผู้ใช้เล่นต่อได้ขณะที่ หน้าจอปิดอยู่ เมื่อทริกเกอร์การเล่นที่ผู้ใช้เริ่มต้นเกิดขึ้น แอปของคุณควรยังคงเริ่มบริการที่ทำงานอยู่เบื้องหน้า

    การทำเช่นนี้จะช่วยให้มั่นใจได้ว่าบริการที่ทำงานอยู่เบื้องหน้าจะเริ่มต้นด้วยความสามารถของ WIU

  • เปิดใช้งาน mediaPlayback FGS ต่อไปในระหว่างที่เกิดข้อผิดพลาดชั่วคราวที่ใช้เวลาไม่ถึง 10 นาที

    หากแอปมีข้อผิดพลาดชั่วคราว เช่น ปัญหาเกี่ยวกับการบัฟเฟอร์เนื่องจาก กิจกรรมเครือข่าย หรือมีการหยุดชะงักชั่วคราวที่คาดไว้ เช่น AUDIOFOCUS_LOSS_TRANSIENT ความตั้งใจที่จะเล่นควรดำเนินต่อไป ดังนั้น FGS ของคุณจึงควรยังคงใช้งานได้

  • หยุดบริการที่ทำงานอยู่เบื้องหน้าที่ส่วนท้ายของการเล่น และเริ่มการเล่นใหม่เฉพาะในกรณีที่ผู้ใช้กลับมาเล่นต่ออย่างชัดแจ้ง

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

    ต่อมา หากผู้ใช้กลับมาเล่นอย่างชัดเจน เช่น ผ่าน UI ของแอปหรือปุ่มเล่นของออบเจ็กต์สื่อแบบสากล ความตั้งใจที่จะเริ่มเล่นเสียงควรกลับมา ซึ่งส่งผลให้ FGS เริ่มต้นใหม่

  • ทดสอบลักษณะการทำงานของการเล่นเสียงด้วยคำสั่ง adb shell

การทดสอบการเปลี่ยนแปลงใน Android 16 และ Android 17

ฟีเจอร์นี้มีการติดตั้งใช้งานที่ระดับ "คำเตือน" ตั้งแต่ Android 16 เป็นต้นไป ซึ่งหมายความว่าแอปสามารถใช้ adb shell cmd audio set-enable-hardening เพื่อทดสอบการบังคับใช้การเพิ่มความปลอดภัยของเสียงในเบื้องหลังด้วยตนเองได้

หากต้องการเปิดใช้การบังคับใช้ในอุปกรณ์ที่ใช้ Android 16 ให้เรียกใช้ คำสั่งต่อไปนี้

adb shell cmd audio set-enable-hardening 1

หากต้องการปิดใช้การบังคับใช้ในอุปกรณ์ที่ใช้ Android 17 ให้เรียกใช้คำสั่งต่อไปนี้

adb shell cmd audio set-enable-hardening 0

นอกจากนี้ เราขอแนะนำให้ใช้ logcat หรือคำสั่ง adb adb dumpsys audio เพื่อ ระบุว่าแอป พบข้อผิดพลาดแบบเงียบเนื่องจากการบังคับใช้การเพิ่มความปลอดภัยของเสียงหรือไม่ หากเป็นเช่นนั้น บันทึกจะมีรายการที่นำหน้าด้วย AudioHardening พร้อมชื่อแพ็กเกจของคุณ

ทำความเข้าใจ FGS ที่มีความสามารถขณะใช้งาน

โดยทั่วไปแล้ว ต้องเปิดใช้บริการที่ทำงานอยู่เบื้องหน้า (FGS) ขณะที่แอปทำงานอยู่เบื้องหน้าเพื่อขยายการดำเนินการที่ผู้ใช้เริ่มต้น ในบางกรณี แอปได้รับอนุญาตให้เปิดใช้บริการที่ทำงานอยู่เบื้องหน้าขณะที่แอปทำงานอยู่ใน เบื้องหลัง อย่างไรก็ตาม โดยปกติแล้วระบบจะไม่ให้ความสามารถขณะใช้งาน (WIU) แก่บริการที่ทำงานอยู่เบื้องหน้าเหล่านี้

WIU ทำหน้าที่เป็นประตูรักษาความปลอดภัย โดยจะป้องกันไม่ให้ FGS ที่เริ่มต้นจากเบื้องหลัง มีส่วนร่วมในพฤติกรรมที่ละเอียดอ่อนบางอย่างในกรณีที่ผู้ใช้อาจไม่ทราบ กิจกรรมของแอป ซึ่งจะป้องกันไม่ให้แอปเข้าถึงข้อมูลที่ละเอียดอ่อน เช่น ตำแหน่ง กล้อง หรือไมโครโฟน และตั้งแต่ Android 17 เป็นต้นไป ก็จะบล็อก API เสียง ที่มักต้องใช้บริบท UI ที่มองเห็นได้ด้วย

ดูข้อมูลอ้างอิงที่มีประโยชน์ได้ที่นี่

  • FGS มาตรฐาน: บริการที่เริ่มต้นขณะที่แอปมองเห็นได้หรือได้รับความสามารถในการเปิดกิจกรรมในเบื้องหลังจะได้รับสิทธิ์เข้าถึง WIU
  • FGS ที่เริ่มต้นในเบื้องหลัง (BFSL): ส่วนใหญ่ไม่ได้ให้สิทธิ์เข้าถึง WIU ข้อยกเว้นหลักที่อนุญาตให้ใช้ WIU คือการโต้ตอบที่เกี่ยวข้องกับความตั้งใจของผู้ใช้ อย่างชัดเจน เช่น การคลิกการแจ้งเตือน การโต้ตอบกับวิดเจ็ต หรือเหตุการณ์ ปุ่มสื่อจากอุปกรณ์ภายนอก
  • ระบบเริ่ม FGS: FGS ที่เริ่มใช้การมอบสิทธิ์ของเซิร์ฟเวอร์ระบบ (เช่น โดยใช้ไลบรารี Jetpack ของ Telecom) จะได้รับสิทธิ์เข้าถึง WIU

อ่านเพิ่มเติมได้ในข้อจำกัดในการเริ่มบริการที่ทำงานอยู่เบื้องหน้าจาก เบื้องหลัง

รายการ API เสียงทั้งหมดที่ได้รับผลกระทบ

ฟังก์ชันเสียง

ผลลัพธ์

API ที่ได้รับผลกระทบ

การเล่นเสียง

ปิดเสียงการเล่น

ไม่มีข้อยกเว้น ไม่มีข้อความแสดงข้อผิดพลาดจาก API ใดๆ

AudioTrack.write()

(NDK) AAudioStream_write

OpenSL ES สำหรับ Android

ไลบรารีสื่อฝั่งไคลเอ็นต์ที่จัดการการเล่น เช่น media3, Exoplayer และ Oboe อาจได้รับผลกระทบด้วย

คำขอโฟกัสเสียง

การคืนสินค้า AUDIOFOCUS_REQUEST_FAILED

ไม่มีผลต่อการเล่นเสียงของแอปอื่นๆ ไม่มีการโฟกัส

AudioManager.requestAudioFocus()

API ระดับเสียงและโหมดเสียงเรียกเข้า

ไม่มีผลต่อโหมดหรือระดับเสียงเรียกเข้า (ระบบจะไม่สนใจการเรียกเมธอดโดยไม่มีการแจ้งเตือน)

ไม่มีข้อยกเว้น ไม่มีข้อความแสดงข้อผิดพลาดจาก API ใดๆ

AudioManager.setStreamVolume()

AudioManager.setStreamMute()

AudioManager.adjustStreamVolume()

AudioManager.adjustVolume()

AudioManager.adjustSuggestedStreamVolume()

AudioManager.setRingerMode()