当前位置: 首页 > news >正文

关于Android 11、12和13服务保活问题

在这里插入图片描述

物联网环境,为了解决不同厂商、不同设备、不同网络情况下使用顺畅,同时也考虑到节约成本,缩小应用体积的好处,我们需要一个服务应用一直存在系统中,保活它以提供服务给其他客户端调用。
开机自启动,通过广播通信,

必要权限

    <!--允许查看所有未启动的应用--><uses-permission android:name="android.permission.QUERY_ALL_PACKAGES"tools:ignore="QueryAllPackagesPermission" /><!--// 添加接收开机广播的权限--><uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" /><!--前台服务--><uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>

开机自启动Service相关代码

import android.content.BroadcastReceiver
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.os.Build
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch/*** @date 2023/2/28* @email L2279833535@163.com* @author 小红妹* @package com.xxx.xxx.receiver* @describe 接收开机广播、开机自启动Service* @copyright*/
class BootBroadcastReceiver : BroadcastReceiver() {private val ACTION_BOOT = "android.intent.action.BOOT_COMPLETED"override fun onReceive(context: Context?, intent: Intent?) {if (intent?.action == ACTION_BOOT) {GlobalScope.launch(Dispatchers.Main) {delay(20000L)val intent = Intent()intent.component =ComponentName("com.xxx.xxx.end", "com.xxx.xxx.end.DeviceService")if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {context?.startForegroundService(intent)} else {context?.startService(intent)}}}}}
import android.app.*
import android.content.Context
import android.content.Intent
import android.content.IntentFilter
import android.graphics.Color
import android.os.Build
import android.os.IBinder
import android.util.Log
import androidx.core.app.NotificationCompat
import com.ccbft.pda.reader.RfidUHF
import com.krd.ricemachine.uits.ShareUtil
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch/*** @date 2023/3/16* @email L2279833535@163.com* @author 小红妹* @package com.xxx.xxx.end* @describe* @copyright*/
class DeviceService : Service() {private lateinit var deviceBroadcastReceiver : DeviceBroadcastReceiverprivate lateinit var mContext: Contextprivate val TAG = "DeviceService"/** 标记服务是否启动 */private var serviceIsLive = false/** 唯一前台通知ID */private val NOTIFICATION_ID = 1000override fun onCreate() {super.onCreate()mContext = this//前台显示服务// 获取服务通知val notification: Notification = createForegroundNotification()//将服务置于启动状态 ,NOTIFICATION_ID指的是创建的通知的IDstartForeground(NOTIFICATION_ID, notification)}override fun onBind(p0: Intent?): IBinder? {return null}override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {CoroutineScope(Dispatchers.Main).launch {//delay(1000L)//阻塞时间//receiverRegist()RfidUHF.initUHF()ShareUtil.putString("AES_key", intent?.getStringExtra("key"), mContext)Log.e(TAG, "onStartCommand: "+ intent?.getStringExtra("key"))}// 标记前台服务启动serviceIsLive = truereturn super.onStartCommand(intent, flags, startId)}private fun receiverRegist() {deviceBroadcastReceiver = DeviceBroadcastReceiver()val filter = IntentFilter()filter.addAction("deviceCall")registerReceiver(deviceBroadcastReceiver, filter)}/*** 创建前台服务通知*/private fun createForegroundNotification(): Notification {val notificationManager = getSystemService(NOTIFICATION_SERVICE) as NotificationManager// 唯一的通知通道的id.val notificationChannelId = "notification_channel_id_01"// Android8.0以上的系统,新建消息通道if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {//用户可见的通道名称val channelName = "Foreground Service Notification"//通道的重要程度val importance = NotificationManager.IMPORTANCE_HIGHval notificationChannel =NotificationChannel(notificationChannelId, channelName, importance)notificationChannel.description = "Channel description"//LED灯notificationChannel.enableLights(true)notificationChannel.lightColor = Color.RED//震动notificationChannel.vibrationPattern = longArrayOf(0, 1000, 500, 1000)notificationChannel.enableVibration(true)notificationManager?.createNotificationChannel(notificationChannel)}val builder = NotificationCompat.Builder(this, notificationChannelId)//通知小图标builder.setSmallIcon(R.mipmap.ic_launcher)//通知标题builder.setContentTitle("AndroidServer")//通知内容builder.setContentText("AndroidServer服务正在运行中")//设定通知显示的时间builder.setWhen(System.currentTimeMillis())//设定启动的内容val activityIntent = Intent(this, MainActivity::class.java)val pendingIntent = PendingIntent.getActivity(this,1,activityIntent,PendingIntent.FLAG_IMMUTABLE) /*FLAG_UPDATE_CURRENT*/builder.setContentIntent(pendingIntent)//创建通知并返回return builder.build()}override fun onDestroy() {//unregisterReceiver(deviceBroadcastReceiver)super.onDestroy()// 标记服务关闭serviceIsLive = false// 移除通知stopForeground(true)}

注意
1、Android 8.0后台运行服务需要开启前台显示服务
2、Android 8.0 不再允许后台进程直接通过startService方式去启动服务,改为startForegroundService方式启动。
对应错误提示如下

Context.startForegroundService() did not then call Service.startForeground(): 
ServiceRecord{24fafff u0 com.xxx.xxx.end/.DeviceService}

3、Android O 后台应用想启动服务调用:调用startForegroundService()后 切记调用startForeground(),这个时候会有一个Notification常驻,也就是上面说的1。
权限提示:

Permission Denial: startForeground from pid=2406, uid=10134 requires 
android.permission.FOREGROUND_SERVICE

4、Android 11以上启动服务不能只是这样简单的调用//context?.startService(Intent(context, DeviceService::class.java))
不然会报错,

Process: com.xuanyi.webserver, PID: 2455
java.lang.IllegalStateException: Not allowed to start service Intent { cmp=com.xxx.xxx/.service.WebService }: app is in background uid UidRecord{103aaa1 u0a138 CEM  idle change:cached procs:1 seq(0,0,0)}at android.app.ContextImpl.startServiceCommon(ContextImpl.java:1715)at android.app.ContextImpl.startService(ContextImpl.java:1670)at android.content.ContextWrapper.startService(ContextWrapper.java:720)at android.content.ContextWrapper.startService(ContextWrapper.java:720)at com.xxx.xxx.receiver.BootBroadcastReceiver$onReceive$1.invokeSuspend(BootBroadcastReceiver.kt:26)at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:570)at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:749)at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:677)at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:664)Suppressed: kotlinx.coroutines.DiagnosticCoroutineContextException: [StandaloneCoroutine{Cancelling}@e0016fc, Dispatchers.Default]

5、Android 12 四大组件含有< intent-filter >< /intent-filter >的需要添加android:exported=“true”,更多情况情况着这篇文章 Android 12适配安全组件导出设置android:exported 指定显式值”

6、Android 11引入了包可见性 ,要么添加QUERY_ALL_PACKAGES权限,要么这样写

<queries>//你要交互的service的包名<package android:name="com.XXX.XXX" />//...等等包名
</queries>

广播通信的前提,1.应用APP要启动过一次,2、要有至少有一个activity ,3、注册广播方式
这就是为什么我们需要服务的意思,首先需要开机自启动服务,这会我们可以在启动的服务中动态注册广播,测试静态注册也可以。
对了,广播的静态注册效果随着版本的升高,效果大打折扣,为了防止小人作弊,系统把君子和小人都设防了。

若是用户手动从后台杀掉应用程序,那么广播无法再次启动服务,哈哈哈哈哈哈,那就想办法让用户无法删除服务吧!

相关文章:

关于Android 11、12和13服务保活问题

物联网环境&#xff0c;为了解决不同厂商、不同设备、不同网络情况下使用顺畅&#xff0c;同时也考虑到节约成本&#xff0c;缩小应用体积的好处&#xff0c;我们需要一个服务应用一直存在系统中&#xff0c;保活它以提供服务给其他客户端调用。 开机自启动&#xff0c;通过广播…...

Java 泛型 使用案例

参考资料 Java 基础 - 泛型机制详解路人甲-Java泛型专题 目录一. 通用Mapper1.1 实体类1.2 Mapper基类1.3 自定义接口1.4 抽象基类Service1.5 调用二. session和bean的获取一. 通用Mapper 1.1 实体类 ⏹ Accessors(chain true): 允许链式调用 import lombok.Data; import …...

进程与线程

文章目录什么是线程线程与进程的关系线程与进程的区别什么是线程 上一篇文章中我们介绍了什么进程&#xff0c;我们把进程比作一个工厂&#xff0c;那么线程就是工厂中的流水线。引入进程的目的就是为了实现多个任务并发执行&#xff0c;但是如果频繁的创建销毁进程&#xff0…...

骑友,怎么挑选适合自己的赛事

骑友&#xff0c;怎么挑选适合自己的赛事一、从场地、路况、天气&#xff0c;各个方面了解赛事的要求。二、看完赛事&#xff0c;要知道自己适合参加什么样的比赛。三、通过比赛成绩&#xff0c;对比自己的实力。四、综合考虑自己的经济能力&#xff0c;根据自己的经济能力选择…...

【Java 数据结构与算法】-遍历Map和Set的方式

作者&#xff1a;学Java的冬瓜 博客主页&#xff1a;☀冬瓜的主页&#x1f319; 专栏&#xff1a;【Java 数据结构与算法】 文章目录一、遍历Map法一 先获取Map集合的全部key的set集合&#xff0c;遍历map的key的Set集合法二 把map的key和value打包成Set的key后的这个Set集合法…...

组件、套件、 中间件、插件

组件、套件、 中间件、插件 组件 位于框架最底层&#xff0c;是由重复的代码提取出来合并而成。组件的本质&#xff0c;是一件产品&#xff0c;独立性很强&#xff0c;组件的核心&#xff0c;是复用&#xff0c;与其它功能又有强依赖关系。 模块 在中台产品和非中台产品中&…...

自动化工具 pytest 内核测试平台落地初体验

测试平台&#xff0c;有人说它鸡肋&#xff0c;有人说它有用&#xff0c;有人说它轮子&#xff0c;众说纷纭&#xff0c;不如从自身出发&#xff0c;考虑是否要做测试平台&#xff1a; 第 1 阶段&#xff0c;用 Pythonrequests 写接口自动化。 第 2 阶段&#xff0c;选择 unit…...

Python 自动化指南(繁琐工作自动化)第二版:四、列表

原文&#xff1a;https://automatetheboringstuff.com/2e/chapter4/ 在开始认真编写程序之前&#xff0c;您需要理解的另一个主题是列表数据类型及其表亲元组。列表和元组可以包含多个值&#xff0c;这使得编写处理大量数据的程序更加容易。由于列表本身可以包含其他列表&#…...

大数据领域的发展及其对现实世界的价值

大数据已经成为全球各行业领域不可或缺的一部分&#xff0c;并且其应用不断涌现。尽管很多人最初对“大数据”这一术语表示怀疑和不信任&#xff0c;但大数据技术已经确立了稳定的发展方向。根据调研机构的预测&#xff0c;到2027年&#xff0c;全球大数据市场规模将达到1090亿…...

几种常见的架构模式

本文已经收录到Github仓库&#xff0c;该仓库包含计算机基础、Java基础、多线程、JVM、数据库、Redis、Spring、Mybatis、SpringMVC、SpringBoot、分布式、微服务、设计模式、架构、校招社招分享等核心知识点&#xff0c;欢迎star~ Github地址 如果访问不了Github&#xff0c…...

flutter安装各种问题汇总

C:\Users\Administrator>flutter doctor -v Flutter assets will be downloaded from https://storage.flutter-io.cn. Make sure you trust this source! [√] Flutter (Channel stable, 3.7.0, on Microsoft Windows [版本 10.0.19044.1826], locale zh-CN) • Flutte…...

网络传输层

目录传输层再谈端口号端口号范围划分认识知名端口号netstatpidofUDP协议UDP协议端格式UDP的特点面向数据报UDP的缓冲区UDP使用注意事项使用udp协议 的应用层协议其它TCP协议TCP协议段格式如何理解链接如何理解三次握手如何理解四次挥手概念TIME_WAIT/CLOSE_WAITTCP策略确认应答…...

linux内核启动分析(二)

文章目录1. set_task_stack_end_magic2.smp_setup_processor_id3. debug_objects_early_init4. cgroup_init_early4.1 init_cgroup_root4.1.1 init_cgroup_housekeeping4.2 cgroup_init_subsys5. local_irq_disable5.1 raw_irqs_disabled5.2 raw_local_irq_disable5.3 trace_ha…...

『EasyNotice』.NET开源消息通知组件——快速实现邮件/钉钉告警通知

&#x1f4e3;读完这篇文章里你能收获到 傻瓜式扩展方法直接使用如何通过EasyNotice快速实现钉钉/邮件的通知发送感谢点赞收藏&#xff0c;避免下次找不到~ 文章目录一、EasyNotice1. 功能介绍2. 源码地址二、项目接入1. 发送邮件通知Step 1 : 安装包&#xff0c;通过Nuget安装…...

JVM垃圾回收算法

垃圾标记阶段 对象存活判断&#xff1a;在堆里存放着几乎所有的Java对象实例&#xff0c;在GC执行垃圾回收之前&#xff0c;首先需要区分出内存中哪些是存活对象&#xff0c;哪些是已经死亡的对象。只有被标记为己经死亡的对象&#xff0c;GC才会在执行垃圾回收时&#xff0c;…...

怎么看待ChatGPT封号这件事呢?

最近的ChatGPT大量封号&#xff0c;刷爆了全网&#xff0c;我的两个个人账号被封禁了&#xff0c;不知道大家最近有没有遇到相关的报错信息&#xff0c;要么就是检查你当前的浏览器配置&#xff0c;最后来一个access denied&#xff0c;要么直接就给你来一个当前的国家不支持。…...

八、交换技术原理

&#xff08;一&#xff09;交换机 1、交换机介绍 一种用于电&#xff08;光&#xff09;信号转发的网络设备&#xff0c;可以为接入交换机的任意两个网络节点提供独享的电信号通路。 工作于第二层的叫交换机&#xff0c;工作于第三层的叫第三层交换机&#xff0c;最常见的是…...

什么是DHCP?DHCP有什么用?(中科三方)

在IP网络中&#xff0c;每一个连接的设备都需要分配一个唯一的IP地址&#xff0c;才能实现和Internet上其他设备的互联。在一些终端规模较大的网络中&#xff0c;需要为每一个主机手工配置IP地址&#xff0c;以避免IP地址的重复&#xff0c;如果主机发生变更&#xff0c;还要去…...

算法设计-二分

一、有序和单调 ​ 二分本质上是一种更加智能的搜索状态空间的方式&#xff0c;他需要状态空间的状态呈现一种“有序的一维数组”的形式&#xff0c;然后再进行搜索。所以一开始的排序是无法避免的。 ​ 因为二分的写法问题&#xff0c;所以应当怎样排序也是有一定讲究的&…...

隧道技术基础

隧道技术基础基本概念端口转发应用层代理基本概念 攻击者通过边界主机进入内网&#xff0c;往往会利用它当跳板进行横向渗透&#xff0c;但现在的内部网络大多部署了很多安全设备&#xff0c;网络结构错综复杂&#xff0c;对于某些系统的访问会受到各种阻挠&#xff0c;这就需…...

智慧工地云平台源码,基于微服务架构+Java+Spring Cloud +UniApp +MySql

智慧工地管理云平台系统&#xff0c;智慧工地全套源码&#xff0c;java版智慧工地源码&#xff0c;支持PC端、大屏端、移动端。 智慧工地聚焦建筑行业的市场需求&#xff0c;提供“平台网络终端”的整体解决方案&#xff0c;提供劳务管理、视频管理、智能监测、绿色施工、安全管…...

【ROS】Nav2源码之nav2_behavior_tree-行为树节点列表

1、行为树节点分类 在 Nav2(Navigation2)的行为树框架中,行为树节点插件按照功能分为 Action(动作节点)、Condition(条件节点)、Control(控制节点) 和 Decorator(装饰节点) 四类。 1.1 动作节点 Action 执行具体的机器人操作或任务,直接与硬件、传感器或外部系统…...

srs linux

下载编译运行 git clone https:///ossrs/srs.git ./configure --h265on make 编译完成后即可启动SRS # 启动 ./objs/srs -c conf/srs.conf # 查看日志 tail -n 30 -f ./objs/srs.log 开放端口 默认RTMP接收推流端口是1935&#xff0c;SRS管理页面端口是8080&#xff0c;可…...

【碎碎念】宝可梦 Mesh GO : 基于MESH网络的口袋妖怪 宝可梦GO游戏自组网系统

目录 游戏说明《宝可梦 Mesh GO》 —— 局域宝可梦探索Pokmon GO 类游戏核心理念应用场景Mesh 特性 宝可梦玩法融合设计游戏构想要素1. 地图探索&#xff08;基于物理空间 广播范围&#xff09;2. 野生宝可梦生成与广播3. 对战系统4. 道具与通信5. 延伸玩法 安全性设计 技术选…...

docker 部署发现spring.profiles.active 问题

报错&#xff1a; org.springframework.boot.context.config.InvalidConfigDataPropertyException: Property spring.profiles.active imported from location class path resource [application-test.yml] is invalid in a profile specific resource [origin: class path re…...

NPOI Excel用OLE对象的形式插入文件附件以及插入图片

static void Main(string[] args) {XlsWithObjData();Console.WriteLine("输出完成"); }static void XlsWithObjData() {// 创建工作簿和单元格,只有HSSFWorkbook,XSSFWorkbook不可以HSSFWorkbook workbook new HSSFWorkbook();HSSFSheet sheet (HSSFSheet)workboo…...

解读《网络安全法》最新修订,把握网络安全新趋势

《网络安全法》自2017年施行以来&#xff0c;在维护网络空间安全方面发挥了重要作用。但随着网络环境的日益复杂&#xff0c;网络攻击、数据泄露等事件频发&#xff0c;现行法律已难以完全适应新的风险挑战。 2025年3月28日&#xff0c;国家网信办会同相关部门起草了《网络安全…...

jmeter聚合报告中参数详解

sample、average、min、max、90%line、95%line,99%line、Error错误率、吞吐量Thoughput、KB/sec每秒传输的数据量 sample&#xff08;样本数&#xff09; 表示测试中发送的请求数量&#xff0c;即测试执行了多少次请求。 单位&#xff0c;以个或者次数表示。 示例&#xff1a;…...

嵌入式学习之系统编程(九)OSI模型、TCP/IP模型、UDP协议网络相关编程(6.3)

目录 一、网络编程--OSI模型 二、网络编程--TCP/IP模型 三、网络接口 四、UDP网络相关编程及主要函数 ​编辑​编辑 UDP的特征 socke函数 bind函数 recvfrom函数&#xff08;接收函数&#xff09; sendto函数&#xff08;发送函数&#xff09; 五、网络编程之 UDP 用…...

书籍“之“字形打印矩阵(8)0609

题目 给定一个矩阵matrix&#xff0c;按照"之"字形的方式打印这个矩阵&#xff0c;例如&#xff1a; 1 2 3 4 5 6 7 8 9 10 11 12 ”之“字形打印的结果为&#xff1a;1&#xff0c;…...