猿湿Xoong的技术栈Android技术知识Android开发经验谈

咦,Oreo怎么收不到广播了?

2018-05-07  本文已影响166人  是天哥哥啊
本文已同步发送到微信公众号:猿湿Xoong

忙啊~最近好忙呀。

忙的我连SystemUI系列的文章推进向蜗牛一样慢~

这篇文章偷个闲,记录下Android8.0上的广播限制。

最近在基于Android 8.1的系统项目中有用到静态注册广播去监听广播。可是不论我是普通的将Apk install进去抑或是高贵的push到对应的system/priv-app/目录下,都收不到这个广播。心态,DUANG,炸了。

后来灵光一闪,扒出记忆角落的Android7.0的广播限制,赶紧Google一下。原来如此,恍然大悟:Android8.0后,当App targetSDK >= 26,几乎禁止了所有的隐式广播的静态注册监听。特在此记录,防止我以后又提莫的忘记了。

本篇文章主要讲述以下内容,还请拿起小板凳,带好零食,前来观赏:

科普科普广播知识

来来来,先科普下,广播两种监听/接收注册方式和两种类型,拿小本本记下来,记住了!

注册方式

两种类型

Intent.setComponent()
Intent.setClassName()
Intent.setClass()
new Intent(A.this,B.class)

Android8.0的后台执行限制

注意是针对targetSDK >= 26的应用,也就是说,targetSDK小于26的话,暂不受影响

在Oreo中,为了进一步提升用户体验,进一步节省功耗,对应用在后台运行时可以执行的操作又进一步施加了限制。

这里多说一句,Android手机的卡顿,很大程度是由于应用滥用且自私的使用各种手段(权限滥用,广播注册,后台服务常驻等)保活或做一些PY事情。Google显然很早就意识到这一点,并从Android 6.0 开始就逐步引入各种限制,比如运行时权限和Doze。

具体广播限制和对应赦免清单

如果应用注册了广播接收器,那么每次发送广播后,应用的广播接收器就会消耗资源,如RAM,CPU等。如果有很多应用对系统事件广播注册广播接收器,这....,就会很卡的嘛!

所以从Android 7.0 (API 级别 24)开始,就对广播做了一些限制:

只不过,在Android8.0上,又进一步的增强了限制,除了以下隐式广播外,其他所有隐式广播均无法通过在AndroidManifest.xml中注册监听。参考官网

// Android 8.0 上不限制的隐式广播
/**
开机广播
 Intent.ACTION_LOCKED_BOOT_COMPLETED
 Intent.ACTION_BOOT_COMPLETED
*/
"保留原因:这些广播只在首次启动时发送一次,并且许多应用都需要接收此广播以便进行作业、闹铃等事项的安排。"

/**
增删用户
Intent.ACTION_USER_INITIALIZE
"android.intent.action.USER_ADDED"
"android.intent.action.USER_REMOVED"
*/
"保留原因:这些广播只有拥有特定系统权限的app才能监听,因此大多数正常应用都无法接收它们。"
    
/**
时区、ALARM变化
"android.intent.action.TIME_SET"
Intent.ACTION_TIMEZONE_CHANGED
AlarmManager.ACTION_NEXT_ALARM_CLOCK_CHANGED
*/
"保留原因:时钟应用可能需要接收这些广播,以便在时间或时区变化时更新闹铃"

/**
语言区域变化
Intent.ACTION_LOCALE_CHANGED
*/
"保留原因:只在语言区域发生变化时发送,并不频繁。 应用可能需要在语言区域发生变化时更新其数据。"

/**
Usb相关
UsbManager.ACTION_USB_ACCESSORY_ATTACHED
UsbManager.ACTION_USB_ACCESSORY_DETACHED
UsbManager.ACTION_USB_DEVICE_ATTACHED
UsbManager.ACTION_USB_DEVICE_DETACHED
*/
"保留原因:如果应用需要了解这些 USB 相关事件的信息,目前尚未找到能够替代注册广播的可行方案"

/**
蓝牙状态相关
BluetoothHeadset.ACTION_CONNECTION_STATE_CHANGED
BluetoothA2dp.ACTION_CONNECTION_STATE_CHANGED
BluetoothDevice.ACTION_ACL_CONNECTED
BluetoothDevice.ACTION_ACL_DISCONNECTED
*/
"保留原因:应用接收这些蓝牙事件的广播时不太可能会影响用户体验"

/**
Telephony相关
CarrierConfigManager.ACTION_CARRIER_CONFIG_CHANGED
TelephonyIntents.ACTION_*_SUBSCRIPTION_CHANGED
TelephonyIntents.SECRET_CODE_ACTION
TelephonyManager.ACTION_PHONE_STATE_CHANGED
TelecomManager.ACTION_PHONE_ACCOUNT_REGISTERED
TelecomManager.ACTION_PHONE_ACCOUNT_UNREGISTERED
*/
"保留原因:设备制造商 (OEM) 电话应用可能需要接收这些广播"

/**
账号相关
AccountManager.LOGIN_ACCOUNTS_CHANGED_ACTION
*/
"保留原因:一些应用需要了解登录帐号的变化,以便为新帐号和变化的帐号设置计划操作"

/**
应用数据清除
Intent.ACTION_PACKAGE_DATA_CLEARED
*/
"保留原因:只在用户显式地从 Settings 清除其数据时发送,因此广播接收器不太可能严重影响用户体验"
    
/**
软件包被移除
Intent.ACTION_PACKAGE_FULLY_REMOVED
*/
"保留原因:一些应用可能需要在另一软件包被移除时更新其存储的数据;对于这些应用,尚未找到能够替代注册此广播的可行方案"

/**
外拨电话
Intent.ACTION_NEW_OUTGOING_CALL
*/
"保留原因:执行操作来响应用户打电话行为的应用需要接收此广播"
    
/**
当设备所有者被设置、改变或清除时发出
DevicePolicyManager.ACTION_DEVICE_OWNER_CHANGED
*/
"保留原因:此广播发送得不是很频繁;一些应用需要接收它,以便知晓设备的安全状态发生了变化"
    
/**
日历相关
CalendarContract.ACTION_EVENT_REMINDER
*/
"保留原因:由日历provider发送,用于向日历应用发布事件提醒。因为日历provider不清楚日历应用是什么,所以此广播必须是隐式广播。"
    
/**
安装或移除存储相关广播
Intent.ACTION_MEDIA_MOUNTED
Intent.ACTION_MEDIA_CHECKING
Intent.ACTION_MEDIA_EJECT
Intent.ACTION_MEDIA_UNMOUNTED
Intent.ACTION_MEDIA_UNMOUNTABLE
Intent.ACTION_MEDIA_REMOVED
Intent.ACTION_MEDIA_BAD_REMOVAL
*/
"保留原因:这些广播是作为用户与设备进行物理交互的结果:安装或移除存储卷或当启动初始化时(当可用卷被装载)的一部分发送的,因此它们不是很常见,并且通常是在用户的掌控下"

/**
短信、WAP PUSH相关
Telephony.Sms.Intents.SMS_RECEIVED_ACTION
Telephony.Sms.Intents.WAP_PUSH_RECEIVED_ACTION

注意:需要申请以下权限才可以接收
"android.permission.RECEIVE_SMS"
"android.permission.RECEIVE_WAP_PUSH"
*/
"保留原因:SMS短信应用需要接收这些广播"

呼,终于列完了,以上。可以说写的比官网还全~

建议收藏一波防止以后用的到哈。

解决方法

按照官方推荐,对于隐式广播,通过以下方法进行替换。

我选择动态注册的方式来处理这个问题。

好了,关于Oreo的广播限制的唠嗑就先唠到这里。

最近受到一位小伙伴的启发,得到一句话:努力的人,运气和机遇往往都不会差!

共勉!

最后,欢迎关注微信公众号:猿湿Xoong
开心的进行Android高质量干货分享


扫码关注喔

参考链接

[1] Android Oreo 后台执行限制 https://developer.android.com/about/versions/oreo/background#broadcasts

[2] Android Oreo Implicit Broadcast Exceptions https://developer.android.com/guide/components/broadcast-exceptions

[3] Android中显式和隐式intent的特点和区别 https://blog.csdn.net/u014177843/article/details/50596863

[4] Android O行为变更--隐式广播限制 https://blog.csdn.net/hqocshheqing/article/details/76850164

上一篇下一篇

猜你喜欢

热点阅读