Android API 30下开机自启动应用失效问题求助
Android API30开机自启动服务失败问题修复
针对你在API30环境下,BroadcastReceiver能接收开机广播但无法启动服务的问题,以下是具体问题分析和修复方案:
核心问题排查与修复
1. 修正BroadcastReceiver的exported属性
系统发送的BOOT_COMPLETED属于外部广播,你的接收器设置了android:exported="false",会导致系统无法正常触发(即便日志有打印,也可能是测试场景的特殊情况)。同时无需添加DEFAULT category,因为该广播不需要此分类。
修改Manifest中的接收器配置:
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" /> <uses-permission android:name="android.permission.FOREGROUND_SERVICE" /> <!-- 新增前台服务权限 --> <!-- 其他配置 --> <receiver android:name=".Starter" android:enabled="true" android:exported="true" <!-- 改为true --> android:label="StartReceiver"> <intent-filter> <action android:name="android.intent.action.BOOT_COMPLETED" /> </intent-filter> </receiver>
2. 替换废弃的服务启动方式
API26开始PendingIntent.getService()已被废弃,且API30对后台服务启动有严格限制,必须使用前台服务启动方式:
修改Starter类的onReceive方法:
public class Starter extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { Log.e("BOOT_CHECK", "Receiver Arrive_1"); if (Intent.ACTION_BOOT_COMPLETED.equals(intent.getAction())) { Log.e("BOOT_CHECK", "Receiver Arrive_2"); Intent serviceIntent = new Intent(context, NetworkCheckService.class); // 移除FLAG_ACTIVITY_NEW_TASK(该标记仅适用于Activity) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { // API26+必须调用startForegroundService context.startForegroundService(serviceIntent); } else { context.startService(serviceIntent); } Log.e("BOOT_CHECK", "Receiver Arrive_3"); } Log.e("BOOT_CHECK", "Receiver Arrive_4"); } }
3. 实现符合要求的前台服务
API26+要求前台服务必须显示通知,否则系统会在5秒内终止服务。确保NetworkCheckService正确实现:
public class NetworkCheckService extends Service { private static final int NOTIFICATION_ID = 1001; private static final String CHANNEL_ID = "BOOT_START_CHANNEL"; @Override public void onCreate() { super.onCreate(); // 创建通知渠道(API26+强制要求) if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { NotificationChannel channel = new NotificationChannel(CHANNEL_ID, "开机服务通知", NotificationManager.IMPORTANCE_LOW); NotificationManager manager = getSystemService(NotificationManager.class); if (manager != null) { manager.createNotificationChannel(channel); } } // 启动前台服务并显示通知 Notification notification = new NotificationCompat.Builder(this, CHANNEL_ID) .setSmallIcon(R.drawable.ic_launcher_foreground) // 替换为你的应用图标 .setContentTitle("服务运行中") .setContentText("网络检测服务已启动") .setPriority(NotificationCompat.PRIORITY_LOW) .build(); startForeground(NOTIFICATION_ID, notification); } @Nullable @Override public IBinder onBind(Intent intent) { return null; } }
同时在Manifest中注册该服务:
<service android:name=".NetworkCheckService" android:exported="false" />
额外注意事项
- API30及以上,应用必须被用户手动启动过至少一次,才能接收
BOOT_COMPLETED广播(系统安全限制)。 - 将应用加入手机电池优化白名单,避免系统在后台杀死服务。
- 测试时使用系统自带的重启功能,不要直接拔电池,确保
BOOT_COMPLETED广播正常发送。
内容的提问来源于stack exchange,提问作者ravaenee
相关产品推荐
相关产品推荐

