【问题标题】:Debugging a service调试服务
【发布时间】:2011-04-29 19:33:41
【问题描述】:

我编写了一个带有远程接口的服务并将其安装在我的 PC 的 Eclipse AVD 上。我有一个客户端测试工具,它启动并调用服务中的方法。最初,我通过一个控件类和活动安装了该服务,现在我已将其删除,因此该服务的清单如下所示:

<?xml version="1.0" encoding="utf-8"?>
<manifest
xmlns:android="http://schemas.android.com/apk/res/android"
package="com.myname.gridservice"
android:versionCode="1"
android:versionName="1.0">
<application
    android:icon="@drawable/icon"
    android:label="@string/app_name"
    android:debuggable="true">
    <service
        android:enabled="true"
        android:debuggable="true"
        android:name="OverlayService">
        <intent-filter>
            <action android:name="com.myname.OverlayService.SERVICE"/>
            <action android:name="com.myname.gridservice.IRemoteInterface" />
        </intent-filter>
    </service>
 </application>  
</manifest>   

所以没有活动标签。

当我从 Eclipse 中的调试图标启动它时,控制台告诉我它正在安装 apk(它是),但它没有显示为调试线程并且没有触发断点,尽管服务的行为是就客户看到的而言,还可以。如果我将服务标签包装在具有关联类的活动标签中并启动它,那么我可以对其进行调试。

是否可以在不将服务包装在活动中的情况下对其进行调试?

【问题讨论】:

标签: android debugging android-service android-manifest


【解决方案1】:

以下是您可以分四个步骤执行的操作:

第一个:在您的服务的第一个有趣的方法中(我在创建时使用):

/* (non-Javadoc)    
 * @see android.app.Service#onCreate()
 */
@Override
public void onCreate() {
    super.onCreate();
    //whatever else you have to to here...
    android.os.Debug.waitForDebugger();  // this line is key
}

第二:在waitForDebugger命令后的任意位置设置断点。

第三:通过 IDE 中的调试按钮启动应用程序(Eclipse/Android Studio/...)。 (您现在应该已经从清单中删除了主要的启动活动)

最后:启动 adb 并运行命令启动服务:

  • cd $PLATFORM_TOOLS
  • adb shell
  • am startservice -n com.google.android.apps.gtalkservice/com.google.android.gtalkservice.service.GTalkService

【讨论】:

  • 好吧,我刚刚意识到,虽然这在我的模拟设备上运行良好,但在我的 htc Inspire 4g 上根本不起作用。似乎从 cmd 行启动服务的命令有效,但是调试器从不附加。不知道为什么...我已经恢复到按照之前的建议启动主要活动...
  • 请注意,“waitForDebugger”行并不意味着服务将在该行中断。它只是意味着“开始观察断点,然后停止在它们上
  • 警告 - 这也意味着如果真正没有附加调试器,则该语句后面的代码将不会执行。
【解决方案2】:

只要确保您不要忘记代码中的这行代码并发布您的 apk。 如果您尝试在没有调试器的情况下运行您的应用,下面的行将会卡住。

android.os.Debug.waitForDebugger();

您也可以使用以下方法来确定调试器是否已连接:

android.os.Debug.isDebuggerConnected(); //Determine if a debugger is currently attached.

【讨论】:

    【解决方案3】:

    编辑 2018 按钮图标已更改

    这很简单,您可以连接到您的应用程序服务。假设运行调试器不起作用,您可以通过按下带有上图所示箭头图标的调试来按下选择进程选项。选择您的服务,您现在应该可以调试您的服务了。

    【讨论】:

    • 这应该是被接受的答案。它很容易,就像一个魅力。唯一的问题是图像上的按钮称为“将调试器附加到 Android 进程”,它可以在 Run -&gt; Attach debugger to Android process 下找到(这是 Android Studio 3.1.2 中的最后一个选项)。
    【解决方案4】:

    我认为应该使用 android.os.Debug.waitForDebugger() 以编程方式完成;

    【讨论】:

    • 简而言之,它不起作用,至少对于在单独进程中运行的前台服务。
    【解决方案5】:

    这适用于 Android Studio。我想在 Eclipse 中可能有类似的方式。

    1. 在调试模式下运行您的项目
    2. 将调试器附加到您的服务进程

    【讨论】:

      【解决方案6】:

      一些答案​​正确地提到了您想要插入

      android.os.Debug.waitForDebugger(); 
      

      进入服务的第一个有趣的方法。但是,从这些答案中并不清楚,Android Studio 调试器不会在服务启动时自动启动。

      相反,您还需要等到服务启动,然后按下按钮附加到进程(参见 Android Studio 3.6.1 的屏幕截图 .. 它是 debug 按钮右侧的第三个按钮) .您将可以选择要附加到的进程,其中一个是服务的单独进程。然后您可以选择它来完成将调试器附加到服务的过程。

      编辑,2020 年 8 月:按钮图标在 Android Studio 4.0 中是相同的

      【讨论】:

        猜你喜欢
        • 2011-02-07
        • 2013-03-26
        • 1970-01-01
        • 2011-10-23
        • 2018-06-14
        • 2010-10-16
        相关资源
        最近更新 更多