为什么我的服务两次启动?我要返回START_STICKY。
我使用运行方式从Eclipse安装它,并在Windows控制台窗口中启动它:
D:\>adb shell am startservice --user 0 -a android.intent.action.MAIN -n "com.sandbox.mq/.MainService"
Starting service: Intent { act=android.intent.action.MAIN cmp=com.sandbox.mq/.MainService }
在Logcat窗口中,我看到它已经运行了两次!:
09-07 21:49:19.427: D/MQ(14027): Hi, the system is up! Today is: Sep 7, 2014 9:49:19 PM
09-07 21:49:19.427: V/MQ(14027): onStartCommand(). I am INSIDE THE main sERVICE Thread id = 1
09-07 21:49:19.427: V/MQ(14027): BackgroundThread0. Thread id = 866 sent message 0
09-07 21:49:19.427: V/MQ(14027): onStartCommand(). I am INSIDE THE main sERVICE Thread id = 1
09-07 21:49:19.437: V/MQ(14027): BackgroundThread0. Thread id = 869 sent message 0
09-07 21:49:19.437: V/MQ(14027): MessageHandler on thread Thread id = 1 received message 0
09-07 21:49:19.437: V/MQ(14027): MessageHandler on thread Thread id = 1 received message 0
当我从adb安装时,它仍然会启动两次,但是输出是不同的:
adb install MQ.apk
-
09-07 22:07:28.567: D/MQ(14642): Hi, the system is up! Today is: Sep 7, 2014 10:07:28 PM
09-07 22:07:28.567: V/MQ(14642): onStartCommand(). I am INSIDE THE main sERVICE Thread id = 1
09-07 22:07:28.577: V/MQ(14642): onStartCommand(). I am INSIDE THE main sERVICE Thread id = 1
09-07 22:07:28.577: V/MQ(14642): BackgroundThread0. Thread id = 872 sent message 0
09-07 22:07:28.577: V/MQ(14642): MessageHandler on thread Thread id = 1 received message 0
包com.sandbox.mq;
public class StartMainService extends Application {
final static String TAG = "MQ";
public void onCreate() {
super.onCreate();
Context context = getApplicationContext();
Log.d(TAG, "Hi, the system is up! Today is: " + DateFormat.getDateTimeInstance().format(new Date()));
Intent startServiceIntent = new Intent(context, MainService.class);
context.startService(startServiceIntent);
}
}
-
public class MainService extends Service {
final static String TAG = "MQ";
BackgroundThread0 bthread0;
BackgroundThread1 bthread1;
public class MqBinder extends Binder {
public MqBinder(Context ctxt) {
Log.v(TAG, "MqBinder() " + "Thread id = "
+ Thread.currentThread().getId());
}
}
@Override
public IBinder onBind(Intent arg0) {
return new MqBinder(this);
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
Log.v(TAG, "onStartCommand(). I am INSIDE THE main sERVICE "
+ "Thread id = " + Thread.currentThread().getId());
bthread0 = new BackgroundThread0();
if (!bthread0.isAlive()) {
bthread0.start();
} else {
Log.v(TAG, "onStartCommand(). bthread0 was already started");
}
bthread1 = new BackgroundThread1();
if (!bthread1.isAlive()) {
bthread1.start();
} else {
Log.v(TAG, "onStartCommand(). bthread1 was already started");
}
return START_STICKY;
}
private class BackgroundThread0 extends Thread {
Handler b1Handler;
@Override
public void run() {
super.run();
b1Handler = bthread1.b1Handler;
Message msg = b1Handler.obtainMessage(MessageHandler.TYPE0);
b1Handler.sendMessage(msg);
Log.v(TAG, "BackgroundThread0. " + "Thread id = "
+ Thread.currentThread().getId() + " sent message "
+ msg.what);
}
}
private class BackgroundThread1 extends Thread {
public BackgroundThread1() {
super();
b1Handler = new MessageHandler();
}
Handler b1Handler;
@Override
public void run() {
super.run();
Looper.prepare();
Looper.loop();
}
}
private static class MessageHandler extends Handler {
static final int TYPE0 = 0;
static final int TYPE1 = 1;
static final int TYPE2 = 2;
public MessageHandler() {
}
@Override
public void handleMessage(Message msg) {
Log.v(TAG, "MessageHandler on thread " + "Thread id = "
+ Thread.currentThread().getId() + " received message "
+ msg.what);
switch (msg.what) {
case TYPE0:
break;
case TYPE1:
break;
case TYPE2:
break;
}
super.handleMessage(msg);
}
}
}
-
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.sandbox.mq" >
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
<uses-sdk
android:minSdkVersion="19"
android:targetSdkVersion="19" />
<application
android:name="com.sandbox.mq.StartMainService"
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:persistent="true"
android:theme="@style/AppTheme" >
<service android:name="com.sandbox.mq.MainService" android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</service>
</application>
</manifest>
更新:
从下面Ian的答案中,当我注释掉onCreate中的startService调用时,该调用仅被调用一次。
09-08 09:29:10.393: D/MQ(4746): Hi, the system is up! Today is: Sep 8, 2014 9:29:10 AM
09-08 09:29:10.393: V/MQ(4746): onStartCommand(). I am INSIDE THE main sERVICE Thread id = 1
09-08 09:29:10.393: V/MQ(4746): BackgroundThread0. Thread id = 1050 sent message 0
09-08 09:29:10.393: V/MQ(4746): MessageHandler on thread Thread id = 1 received message 0
我的原始问题得到了回答,但我想知道...为什么BackgroundThread1与主服务线程ID = 1具有相同的线程ID?
它启动了两次,因为您启动了两次:
adb shell am startservice
启动服务Application
的onCreate()
,这也将启动服务。onStartCommand
每当有东西开始为您服务时都会调用。如果您只希望在服务的生命周期中执行某项操作,则应使用服务的onCreate()
方法执行该操作,或者在再次执行工作之前进行检查onStartCommand
(即,bthread0
在创建或重新启动它之前检查是否为null)。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句