试图开发Android服务


trying to make an Android service

我正在尝试制作一个Android服务,它应该在设备启动时启动。它应该每5分钟发送位置数据到mySQL数据库,通过POST到php web服务。

应该发送以下数据:

regID = same regId it used to register to GCM
name = a user name
latitude = the current latitude
longitude = the current longitude

我以前从来没有做过服务,所以我很困惑应该怎么做。

如果你能指引我正确的方向,我会很感激的。

这是我到目前为止所做的:

package servicio;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.HttpClient;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.util.EntityUtils;
import android.app.Service;
import android.content.Intent;
import android.location.Criteria;
import android.location.Location;
import android.location.LocationListener;
import android.location.LocationManager;
import android.os.Bundle;
import android.os.IBinder;
import com.google.android.gcm.GCMRegistrar;
public class GeoService extends Service {
    LocationManager manejador;
    String proveedor;
    Location localizacion;
    LocationListener locListener;
    String latitud, longitud;
    final String regId = GCMRegistrar
            .getRegistrationId(getApplicationContext());
    // double latitud, longitud;
    @Override
    public void onCreate() {
        manejador = (LocationManager) getSystemService(LOCATION_SERVICE);
    }
    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Criteria req = new Criteria();
        req.setAccuracy(Criteria.ACCURACY_FINE);
        // Lista de proveedores por criterio
        proveedor = manejador.getBestProvider(req, false);
        localizacion = manejador.getLastKnownLocation(proveedor);
        // location listener
        locListener = new LocationListener() {
            @Override
            public void onLocationChanged(Location location) {
                latitud = String.valueOf(location.getLatitude());
                longitud = String.valueOf(location.getLongitude());
                Thread sendGpsPositionToDB = new Thread(new Runnable() {
                    @Override
                    public void run() {
                        String server = "http://www.grupobcn.es/aquacleanmessenger/";
                        String serverUrl = server + "addposicion.php";
                        List<NameValuePair> params = new ArrayList<NameValuePair>();
                        params.add(new BasicNameValuePair("iddevice", regId));
                        params.add(new BasicNameValuePair("latitud", latitud));
                        params.add(new BasicNameValuePair("longitud", longitud));
                        HttpClient httpclient = new DefaultHttpClient();
                        HttpPost httppost = new HttpPost(serverUrl);
                        try {
                            httppost.setEntity(new UrlEncodedFormEntity(params));
                            HttpResponse response = httpclient
                                    .execute(httppost);
                        } catch (IOException e) {
                        }
                    }
                });
                sendGpsPositionToDB.start();
            }
            @Override
            public void onProviderDisabled(String provider) {
                // TODO Auto-generated method stub
            }
            @Override
            public void onProviderEnabled(String provider) {
                // TODO Auto-generated method stub
            }
            @Override
            public void onStatusChanged(String provider, int status,
                    Bundle extras) {
                // TODO Auto-generated method stub
            }
        };
        manejador.requestLocationUpdates(LocationManager.GPS_PROVIDER, 300000,
                0, locListener);
        return START_STICKY;
    }
    @Override
    public void onDestroy() {
        super.onDestroy();
    }
    @Override
    public IBinder onBind(Intent intencion) {
        return null;
    }
}

可以通过注册广播接收器并定义RECEIVE_BOOT_COMPLETED权限来实现。

当用户安装应用程序时,操作系统将查看清单并注册为自动启动。任何时候设备启动,操作系统将调用你的onReceive(),这样你就可以启动你的服务,如下所示:

在你的manifest中:

<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED" />
<service android:name=".GeoService" />
<receiver android:name="servicio.AutoStartGeo">  
    <intent-filter>  
        <action android:name="android.intent.action.BOOT_COMPLETED" />  
    </intent-filter>  
</receiver>
定义AutoStartGeo类:
public class AutoStartGeo extends BroadcastReceiver{
@Override
public void onReceive(Context context, Intent intent) {
      if (intent.getAction() != null){
    Intent startServiceIntent = new Intent(context, GeoService.class);
    context.startService(startServiceIntent);       
}
}
}

如果应用程序安装在SD卡上,这不会起作用,因为在android.intent.action.BOOT_COMPLETED事件之后,应用程序将不可用。你必须通知用户这一点,或者通过:android:installLocation="internalOnly"

强制你的应用程序在内部安装。

还需要注意的是,在Android 3.0及更高版本上,用户需要在应用程序可以接收Android .intent.action. boot_completed事件之前至少启动一次应用程序。