java - 没有通知的Android前台服务 - 如何?
问题描述
我在我的应用程序中为通知创建了前台服务。它工作正常,问题是启动我们需要前台通知的前台服务,它告诉您的应用程序正在 像这样运行。我不想要这个通知。如何在不终止服务的情况下删除该通知。
这就是我启动前台服务的方式。
@Override
public void onCreate() {
super.onCreate();
stopForeground(true);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel serviceChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, channelName, NotificationManager.IMPORTANCE_DEFAULT);
NotificationManager notificationManager = getSystemService(NotificationManager.class);
notificationManager.createNotificationChannel(serviceChannel);
}
Intent stopSelf = new Intent(this, Notification_Service.class);
stopSelf.setAction("ACTION_STOP_SERVICE");
PendingIntent pStopSelf = PendingIntent
.getService(this, 0, stopSelf
, PendingIntent.FLAG_CANCEL_CURRENT);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID);
NotificationManager notificationManager =
(NotificationManager) getSystemService(Service.NOTIFICATION_SERVICE);
NotificationCompat.Action action =
new NotificationCompat.Action.Builder(
0, "Close", pStopSelf
).build();
Notification notification = notificationBuilder
.setSmallIcon(R.drawable.ic_launcher_background)
.setContentTitle("Ask Question")
.setContentText("Ask Question is running")
.addAction(action)
.setPriority(Notification.PRIORITY_MIN)
.build();
notificationManager.notify(1, notification);
startForeground(1, notification);
notificationManager.cancel(1);
SharedPreferences settings = getSharedPreferences("Session", MODE_PRIVATE);
id = settings.getString("id", null);
apiInterface = ApiClient.getApiClient().create(ApiInterface.class);
handler.postDelayed(new Runnable() {
public void run() {
startMyOwnForeground();
handler.postDelayed(this, delay);
}
}, delay);
}
private void startMyOwnForeground() {
Log.e("", "service running");
get_notification();
}
改造电话以获取通知:
private void get_notification() {
Call<ArrayList> call = apiInterface.getnotification(ApiClient.pin, id);
call.enqueue(new Callback<ArrayList>() {
@RequiresApi(api = Build.VERSION_CODES.N)
@Override
public void onResponse(Call<ArrayList> call, Response<ArrayList> response) {
if (response.body() != null) {
for (int i = 0; i < response.body().size(); i = i + 1) {
ArrayList<String> getdata = (ArrayList<String>) response.body().get(i);
String[] data = getdata.toArray(new String[0]);
if (data[5].equals("0")) {
switch (data[4]) {
case "comment":
send_comment_notification(data[1], data[2], data[3], data[0]);
break;
case "question":
send_question_notification(data[3], data[0], data[1]);
break;
case "answer":
send_answer_notification(data[3], data[0], data[1]);
break;
}
}
}
}
}
@Override
public void onFailure(Call<ArrayList> call, Throwable t) {
}
});
}
解决方案
您似乎正在尝试使用“拉”方法而不是“推”方法来显示通知。为了显示由某些后端系统触发的通知,您通常应该使用推送通知。
只有当您无法控制后端系统时,您才能考虑从服务器中提取定期更新。但即便如此,创建自己的后端(另请参阅BFF 模式)可能会有意义,该后端会拉取更新,然后将推送通知发送到您的应用程序,而不是从服务器拉取每个应用程序。
正如评论中已经建议的那样,您应该使用 FCM 将通知从您的服务器推送到您的应用程序。查看FCM 文档以获得良好的概述。Android 系统和 Firebase SDK 将为您完成繁重的工作,您的应用无需在后台或前台运行即可接收通知。
如果您仍然想从服务器中获取固定的时间间隔,您应该使用WorkManager API 甚至使用同步适配器来实现后台同步机制。然后您可以使用NotificationBuilder
来创建“本地”通知。
推荐阅读
- python - 在目录中创建所有文件名及其文件扩展名的列表
- javascript - 如何将此 React 钩子组件转换为功能组件
- google-cloud-platform - 使用私有 IP 地址和多个私有服务连接启动 CloudSQL
- cassandra - 是否可以限制用户仅查看 Cassandra 中的一组特定列?
- postgresql - 从 jsonb postgresql 获取数组数据
- javascript - 将源 JSON 字符串合并到具有相似键但在 javascript 中具有不同结构的目标
- python - 在 Python 中以交叉表的形式表示从多列之间的卡方检验获得的 p 值
- delphi - 如何共享应用程序和关联的数据文件
- python - Python:为什么当我将 int 或 list 或 tuple 放入列表时结果相同?
- javascript - 添加 javascript 查询动态更改 Oracle Apex 中的按钮标签