保持服务运行

18

有人能告诉我如何让一个服务在用户关闭它后始终保持运行或重新启动吗?我注意到当我清除内存时,Facebook服务会重新启动。 我不想创建前台服务。


对于新的API,您可以使用此链接:https://dev59.com/AHE85IYBdhLWcg3w3Xv6#49878237 - MHSaffari
2个回答

29

你应该创建一个sticky service。可以在onStartCommand中返回START_STICKY来实现该功能。更多信息请参阅这里

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
    Log.i("LocalService", "Received start id " + startId + ": " + intent);
    // We want this service to continue running until it is explicitly
    // stopped, so return sticky.
    return START_STICKY;
}

还可以了解一下application:persistent,它表示“应用程序是否应始终保持运行状态”。这更加麻烦 - 系统将尝试不杀死您的应用程序,这会影响系统中的其他应用程序,因此您应该谨慎使用它。


我认为使用application:persistent不是一个好的做法。我认为这样做会真正增加电池消耗。 - busylee
1
@busylee,你说得对。这对内存负载和电池消耗都不好。希望最后一段就是关于这个的。然而,我更喜欢直接得到/给出答案,而不是建议。 - auselen
1
application:persistent 看起来很不错,但在我的 Android 4.3 上没有效果。显然它只适用于系统应用程序 - Sam
嗨,我已经在onStartCommand中将标志设置为START_STICKY,但是进程仍然会在一段时间后关闭。我该如何解决这个问题? - prakashpun
2
这个方法应该调用 super.onStartCommand(intent, flags, startId)。 - Rafouille

8

我从以前的一个应用程序中使用的服务中复制了这个。

在服务中,请勿更新任何UI,因为您在服务中没有用户界面。这也适用于Toast。

祝好运!

public class nasserservice extends Service {
    private static long UPDATE_INTERVAL = 1*5*1000;  //default

    private static Timer timer = new Timer(); 
    @Override
    public IBinder onBind(Intent intent) {
        // TODO Auto-generated method stub
        return null;
    }

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

    }   

    private void _startService()
    {      
        timer.scheduleAtFixedRate(    

                new TimerTask() {

                    public void run() {

                        doServiceWork();

                    }
                }, 1000,UPDATE_INTERVAL);
        Log.i(getClass().getSimpleName(), "FileScannerService Timer started....");
    }

    private void doServiceWork()
    { 
        //do something wotever you want 
        //like reading file or getting data from network 
        try {
        }
        catch (Exception e) {
        }

    }

    private void _shutdownService()
    {
        if (timer != null) timer.cancel();
        Log.i(getClass().getSimpleName(), "Timer stopped...");
    }

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

        _shutdownService();

        // if (MAIN_ACTIVITY != null)  Log.d(getClass().getSimpleName(), "FileScannerService stopped");
    }

}

抱歉晚回复。答案是肯定的。 - Hossam Alaa
这对我似乎没有任何影响;它没有阻止服务被终止,也没有导致服务在被终止后重新启动。 - Sam
我认为计时器不会被垃圾回收,因为它是不同的线程,而且线程一直在运行,持有对服务本身的引用。 @Sam,我想知道为什么这个解决方案对你不起作用? - HendraWD
@HendraWijayaDjiono,我已经太久没有记得我是如何测试它的了,所以我不确定! :) - Sam

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接