如何防止服务被破坏

时间:2016-08-20 03:48:10

标签: android

我有Service跟踪用户的位置,在我获得GoogleApiClient用户位置的时候。

发生了一些Service停止,依赖于互联网或模型电话,Service停止向webservice发送位置。它好像被毁了。

我该如何防止这种情况?

public class LocationService extends Service implements
        GoogleApiClient.ConnectionCallbacks,
        GoogleApiClient.OnConnectionFailedListener,
        LocationListener {

    private static final String TAG = "LocationService";
    public long UPDATE_MILLISECONDS_DEFAULT = 180000;

    private boolean currentlyProcessingLocation = false;
    private LocationRequest locationRequest;
    private GoogleApiClient googleApiClient;

    @Override
    public void onCreate() {
        Log.d(TAG,"Location service create");
        super.onCreate();
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        // if we are currently trying to get a location and the alarm manager has called this again,
        // no need to start processing a new location.
        if (!currentlyProcessingLocation) {
            currentlyProcessingLocation = true;
            startTracking();
        }

        return START_NOT_STICKY;
    }

    private void startTracking() {
        Log.d(TAG, "startTracking");

        if (GooglePlayServicesUtil.isGooglePlayServicesAvailable(this) == ConnectionResult.SUCCESS) {
            googleApiClient = new GoogleApiClient.Builder(this)
                    .addApi(LocationServices.API)
                    .addConnectionCallbacks(this)
                    .addOnConnectionFailedListener(this)
                    .build();

            if (!googleApiClient.isConnected() || !googleApiClient.isConnecting()) {
                googleApiClient.connect();
            }
        } else {
            Log.e(TAG, "unable to connect to google play services.");
        }
    }

    protected void sendLocationToServer(Location location) {
            // here I call my webservice and send location
            Log.d(TAG, "Update to Server location");
    }

    @Override
    public void onDestroy() {
        Log.d(TAG,"Destroy service");
        stopLocationUpdates();
        super.onDestroy();

    }


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

    @Override
    public void onLocationChanged(Location location) {
       sendLocationToServer(location);
    }

    public void stopLocationUpdates() {
        if (googleApiClient != null && googleApiClient.isConnected()) {
            googleApiClient.disconnect();
        }
    }

    /**
     * Called by Location Services when the request to connect the
     * client finishes successfully. At this point, you can
     * request the current location or start periodic updates
     */
    @Override
    public void onConnected(Bundle bundle) {
        Log.d(TAG, "onConnected");

        locationRequest = LocationRequest.create();
            locationRequest.setInterval(UPDATE_MILLISECONDS_DEFAULT); // milliseconds for default
            locationRequest.setPriority(LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY);


        //locationRequest.setFastestInterval(1000); // the fastest rate in milliseconds at which your app can handle location updates

        LocationServices.FusedLocationApi.requestLocationUpdates(
                googleApiClient, locationRequest, this);
    }

    @Override
    public void onConnectionFailed(ConnectionResult connectionResult) {
        Log.e(TAG, "onConnectionFailed");

        stopLocationUpdates();
        stopSelf();
    }

    @Override
    public void onConnectionSuspended(int i) {
        Log.e(TAG, "GoogleApiClient connection has been suspend");
    }


}

2 个答案:

答案 0 :(得分:5)

您从START_NOT_STICKY返回onStartCommand()

因此,每当操作系统杀死你的Service(例如回收内存)时,它就不会被重新创建。

更改以下行:

return START_NOT_STICKY;

对此:

return START_STICKY;

来自START_STICKY的{​​{3}}:

  

onStartCommand(Intent, int, int)返回的常量:如果是这样的话   服务的进程在启动时被终止(从...返回后)   onStartCommand(Intent, int, int)),然后让它处于启动状态   但是不要保留这个意图。稍后系统会尝试   重新创建服务。因为它处于启动状态,它会   保证在创建后调用onStartCommand(Intent, int, int)   新服务实例;如果没有任何挂起的启动命令   如果被传递给服务,它将被调用null意图   对象,所以你必须注意检查这个。

注意: START_STICKY不会阻止您Service被杀。它只是告诉操作系统尽快重启(取决于可用的资源)。为了使你的Service不太可能被杀,你可以 通过调用documentation使其在前台运行。

答案 1 :(得分:0)

您只需更改此行代码

即可
 @Override
public int onStartCommand(Intent intent, int flags, int startId) {
    // if we are currently trying to get a location and the alarm manager has called this again,
    // no need to start processing a new location.
    if (!currentlyProcessingLocation) {
        currentlyProcessingLocation = true;
        startTracking();
    }

    return START_STICKY;
}