1- /* *
1+ /* *
22 * Copyright 2019-2026, Tomasz Żebrowski
33 *
44 * <p>Licensed to the Apache Software Foundation (ASF) under one or more contributor license
@@ -23,12 +23,14 @@ import android.app.NotificationManager
2323import android.app.PendingIntent
2424import android.app.Service
2525import android.content.Intent
26+ import android.content.pm.ServiceInfo
2627import android.os.Binder
2728import android.os.Build
2829import android.os.IBinder
2930import android.util.Log
3031import androidx.core.app.NotificationCompat
3132import org.obd.graphs.Permissions
33+ import org.obd.graphs.REQUEST_LOCATION_PERMISSIONS
3234import org.obd.graphs.REQUEST_NOTIFICATION_PERMISSIONS
3335import org.obd.graphs.bl.query.Query
3436import org.obd.graphs.datalogger.R
@@ -75,20 +77,7 @@ class DataLoggerService : Service() {
7577
7678 createNotificationChannel()
7779
78- // Handle Foreground Service Types (Android 10+)
79- if (Build .VERSION .SDK_INT >= Build .VERSION_CODES .Q ) {
80- var serviceTypes = android.content.pm.ServiceInfo .FOREGROUND_SERVICE_TYPE_CONNECTED_DEVICE
81-
82- if (Permissions .hasLocationPermissions(this )) {
83- serviceTypes = serviceTypes or android.content.pm.ServiceInfo .FOREGROUND_SERVICE_TYPE_LOCATION
84- } else {
85- Log .w(LOG_TAG , " Location permission missing. Starting Service without GPS capabilities." )
86- }
87-
88- startForeground(NOTIFICATION_ID , createNotification(), serviceTypes)
89- } else {
90- startForeground(NOTIFICATION_ID , createNotification())
91- }
80+ startForegroundServiceSafe()
9281
9382 // Fail-fast if permissions are missing
9483 if (! Permissions .hasNotificationPermissions(this )) {
@@ -168,7 +157,42 @@ class DataLoggerService : Service() {
168157 enqueueWork(ACTION_STOP )
169158 }
170159
171- // --- Helper Methods ---
160+ private fun startForegroundServiceSafe () {
161+ try {
162+ val notification = createNotification()
163+
164+ if (Build .VERSION .SDK_INT >= Build .VERSION_CODES .Q ) {
165+ var serviceTypes = ServiceInfo .FOREGROUND_SERVICE_TYPE_CONNECTED_DEVICE
166+
167+ // Only add LOCATION type if we actually have runtime permission
168+ if (Permissions .hasLocationPermissions(this )) {
169+ serviceTypes = serviceTypes or ServiceInfo .FOREGROUND_SERVICE_TYPE_LOCATION
170+ } else {
171+ Log .w(LOG_TAG , " Location permission missing. Starting Service without GPS capabilities." )
172+ }
173+
174+ startForeground(NOTIFICATION_ID , notification, serviceTypes)
175+ } else {
176+ startForeground(NOTIFICATION_ID , notification)
177+ }
178+ } catch (e: SecurityException ) {
179+ Log .e(LOG_TAG , " Failed to start FGS with requested types. Retrying with basic type." , e)
180+ // Fallback: Try starting without Location to keep the service alive
181+ if (Build .VERSION .SDK_INT >= Build .VERSION_CODES .Q ) {
182+ try {
183+ startForeground(
184+ NOTIFICATION_ID ,
185+ createNotification(),
186+ ServiceInfo .FOREGROUND_SERVICE_TYPE_CONNECTED_DEVICE
187+ )
188+ } catch (e2: Exception ) {
189+ Log .e(LOG_TAG , " CRITICAL: Failed to start FGS even with fallback." , e2)
190+ sendBroadcastEvent(REQUEST_LOCATION_PERMISSIONS )
191+ stopSelf()
192+ }
193+ }
194+ }
195+ }
172196
173197 private fun enqueueWork (
174198 intentAction : String ,
0 commit comments