在安卓系统中运行永无止境的服务的最佳方法。

问题描述 投票:5回答:6

我有一个服务,当用户改变了他的位置时,会发出通知,我想让这个服务一直运行,直到用户在应用程序管理器中明确地强制停止我的应用程序。我想让这个服务一直运行下去,直到用户在应用程序管理器中明确强制停止我的应用程序。我使用了以下方法。

        Intent intent1 = new Intent(context, LocationService2.class);
        PendingIntent contentIntent = PendingIntent.getService(context, 0, intent1, 0);
        AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
        am.setRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP, SystemClock.elapsedRealtime(),2*60000, contentIntent);

服务类:

public class LocationService2 extends Service implements GoogleApiClient.ConnectionCallbacks,GoogleApiClient.OnConnectionFailedListener {
private GoogleApiClient mGoogleApiClient;

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
    Log.v("TAG", "STARTLS");
    mGoogleApiClient = new GoogleApiClient.Builder(this)
                .addConnectionCallbacks(this)
                .addOnConnectionFailedListener(this)
                .addApi(LocationServices.API)
                .build();

    mGoogleApiClient.connect();
    return START_STICKY;
}

@Override
public void onConnected(Bundle bundle) {
    Log.i(TAG, "Location services connected.");

    Location location = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
    // Use this location to give notification if required.
}

@Override
public void onConnectionSuspended(int i) {
    Log.i(TAG, "Location services suspended. Please reconnect.");
}

@Override
public void onConnectionFailed(ConnectionResult connectionResult) {

}

@Nullable
@Override
public IBinder onBind(Intent intent) {
    return null;
}

@Override
public void onDestroy() {
    super.onDestroy();
    mGoogleApiClient.disconnect();
}
}

这个方法并不是在所有的手机上都能使用的。如果是,那么我如何改进这段代码,使其在所有手机上工作?

android android-service alarmmanager
6个回答
2
投票

你应该让你的服务成为一个 Foreground Service. 你可以找到一个教程 此处.


1
投票

舱单条目

<receiver android:name="YourPackagename.RestartReceiver">
<intent-filter>
        <action android:name="android.intent.action.BOOT_COMPLETED" />
</intent-filter>
</receiver>

<receiver android:name="YourPackagename.AlarmReceiver" >
</receiver>

手机重启时需要重新初始化报警管理器。重启接收机.java

public class RestartReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        if (intent.getAction().equals(Intent.ACTION_BOOT_COMPLETED)) {
            AlarmManager alarmMgr = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
            Intent intentReciever = new Intent(context, AlarmReceiver.class);
            PendingIntent alarmIntent = PendingIntent.getBroadcast(context, 0, intentReciever, 0);
            alarmMgr.setRepeating(AlarmManager.RTC_WAKEUP, (System.currentTimeMillis() + GlobalContext.PUSH_NOTIFICATION_INTERVAL),
                    GlobalContext.PUSH_NOTIFICATION_INTERVAL, alarmIntent);
        }
    }

}

警报接收机.java

public class AlarmReceiver extends BroadcastReceiver{

    @Override
    public void onReceive(Context context, Intent intent) {
        //you can put your logic over here
    }
}

在您的闪屏中加入以下代码

private void initService() {
        if(!app_preferences.getBoolean("isServiceRunning", false))
        {
            AlarmManager alarmMgr = (AlarmManager) getSystemService(Context.ALARM_SERVICE);
            Intent intentReciever = new Intent(LoadingScreen.this, AlarmReceiver.class);
            PendingIntent alarmIntent = PendingIntent.getBroadcast(LoadingScreen.this, 0, intentReciever, 0);
            alarmMgr.setRepeating(AlarmManager.RTC_WAKEUP, (System.currentTimeMillis()+GlobalContext.PUSH_NOTIFICATION_INTERVAL),
                    GlobalContext.PUSH_NOTIFICATION_INTERVAL, alarmIntent);
            app_preferences.edit().putBoolean("isServiceRunning", true).commit();
        }
    }

/注意:使用共享偏好来检查你的Alerm服务是否在运行,这不是一个好办法。


0
投票

创建一个永不结束的服务的步骤是。

1.) Start service using alarmManager.
2.) Check in onResume if service is running & restart if not.
3.) Return START_STICKY from onStartCommand().
4.) In OnStartCommand() , create a thread and do the needful from that thread .All the logical stuff should be there in while(true). 

这样你的服务就不会被杀死。


0
投票

在给定的代码中,我已经把一些好的东西,如你可以 沟通活动 使用 订书机服务 通过listner. 您可以通过在服务中编写代码来通知您的活动您失去了网络连接...。

创建 粘性 如果用户杀死应用程序,它将再次自动重新启动。

当与报警管理器相比,你可能会面临重复的多个服务启动,像我们需要识别和防止,如果报警管理器已经我已经创建了,然后不要再次启动,根据我的另一个答案写在同一个问题。

Manifest.xml

<receiver android:name=".BootCompleteReceiver"><intent-filter><action android:name="android.intent.action.BOOT_COMPLETED"/></intent-filter></receiver>
<service android:name=".MyService" android:enabled="true" android:exported="false"/>

MyService.java

public class MyService extends Service {

        CommunicationListner listener;
        public class LocalBinder extends Binder {
            public MyService getService() {
                // Return this instance of LocalService so clients can call public methods
                return MyService.this;
            }
        }


        @Override
        public IBinder onBind(Intent intent) {
            return mBinder;
        }

        @Override
        public void onCreate() {
            super.onCreate();
        }

        @Override
        public int onStartCommand(Intent intent, int flags, int startId) {
            try {
                unregisterReceiver(internetConnectionReceiver);
            } catch (Exception e) {
            }
            registerReceiver(internetConnectionReceiver, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION));
            return START_STICKY;
        }

        @Override
        public void onDestroy() {
            super.onDestroy();
        }

        //communication with activity
        public void registerChatReceivedListener(CommunicationListner listener) {
            this.listener = listener;
        }

        public void removeChatReceivedListener() {
            chatListener = null;
        }


        private BroadcastReceiver internetConnectionReceiver = new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {

            }
        };

        public MyService() {
        }

    }

在重启手机上重新启动服务BootCompleteReceiver.Java

public class BootCompleteReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        if (intent.getAction().equals(Intent.ACTION_BOOT_COMPLETED)) {
            context.startService(new Intent(context, MyService.class));
        }
    }
}

在你的闪屏中加入代码来启动myservice,如果它已经启动了,那么也不用担心。

startService(new Intent(getApplicationContext(), MyService.class));

0
投票

只要服务被杀,就可以随时启动。

@Override
public void onDestroy() {
    super.onDestroy();
    mGoogleApiClient.disconnect();
    startService(new Intent(this, LocationService2.class));
}

0
投票

在安卓5及以上版本中的解决方案是使用AlarmManger和Broadcast Receiver。

© www.soinside.com 2019 - 2024. All rights reserved.