0

シンプルな ServiceTestCase とライフサイクル メソッドのみを含む空の IntentSerice があり、サービスは AndroidManifest.xml にも登録されており、アクション タグ「com.tut.my.service.DATAUPDATE」も登録されています。

Service の呼び出しは非常にうまく機能し、すべてのライブ サイクル メソッドが順番に表示されますが、カスタム テストの終了後に奇妙なことが起こります。ServiceTestCase は、カスタム テストの後にメソッドtestServiceTestCaseSetUpProperly()を発行して、 setupService()が正しく実行されることを確認しました。

だから私は周りを見回して、いくつかの興味深いブログの懸念 setupService() を見つけましたが、結論は満足のいくものではありませんでした。ブログの著者は、いくつかの正当な理由により、setUp()でstartService(...)を呼び出さないことをお勧めしています。

ただし、カスタム テストの後に testServiceTestCaseSetUpProperly() を呼び出すことで発生した問題は、MyService サービスの新しいインスタンスの呼び出しです。これにより、onCreate が呼び出され、サービスが何らかの理由で終了しますが、すべてのテストは成功します。

サービスのソースは次のとおりです。

public class MyService extends IntentService {

  public static final String INTENT = "com.tut.my.service.DATAUPDATE";

  public MyService() {
    super(INTENT);
    Log.d(getClass().getSimpleName(), "called: std c-tor()");
  }

  @Override
  public void onCreate() {
    super.onCreate();
    Log.d(getClass().getSimpleName(), "called: onCreate()");
  }

  @Override
  public int onStartCommand(Intent intent, int flags, int startId) {
    Log.d(getClass().getSimpleName(), "called onStartCommand() --> intent: " + intent.getAction() + " flags: " + flags + " startID: " + startId);
    return super.onStartCommand(intent, flags, startId);
  }

  @Override
  public void onDestroy() {
    super.onDestroy();
    Log.d(getClass().getSimpleName(),"called: onDestory()");
  }

  @Override
  protected void onHandleIntent(Intent intent) {
    Log.d(getClass().getSimpleName(), "called: onHandleIntent() --> Intent: " + intent.getAction());
    setPriceData();
  }
}

ServiceTestCase のソースは次のとおりです。

@MediumTest
public class MyServiceTest extends ServiceTestCase<MyService> {

  Context mCtx = null;

  public MyServiceTest() {
    super(MyService.class);
  }

  @Override
  protected void setUp() throws Exception {
    super.setUp();
    mCtx = getSystemContext();
  }

  @MediumTest
  public void testGetMyServiceData() throws InterruptedException {
    Intent i = new Intent(MyService.INTENT);
    Log.d(getClass().getSimpleName(), "startService(i)");
    mCtx.startService(i);

    // throttle the instrumentation thread so the service 
    // can be instantiated for sure
    Log.d(getClass().getSimpleName(), "before Thread Sleep");
    Thread.sleep(8000); // needs 10 seconds before ANR
    Log.d(getClass().getSimpleName(), "after Thread Sleep");
  }
}

対応する (削除された) LogCat 出力:

I/TestRunner(11954): started: testGetMyServiceData(com.tut.my.service.MyServiceTest)
D/MyServiceTest(11954): startService(i)    
D/MyService(11954): called: std c-tor()
D/MyServiceTest(11954): before Thread Sleep
D/MyService(11954): called: onCreate()
D/MyService(11954): called onStartCommand() --> intent: com.tut.my.service.DATAUPDATE flags: 0 startID: 1
D/MyService(11954): called: onHandleIntent() --> Intent: com.tut.my.service.DATAUPDATE
D/MyService(11954): called: onDestory()
D/MyServiceTest(11954): after Thread Sleep
I/TestRunner(11954): finished: testGetMyServiceData(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): passed: testGetHarvestData(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): started: testServiceTestCaseSetUpProperly(com.tut.my.service.MyServiceTest)
D/MyService(11954): called: std c-tor()
I/TestRunner(11954): finished: testServiceTestCaseSetUpProperly(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): passed: testServiceTestCaseSetUpProperly(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): started: testAndroidTestCaseSetupProperly(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): finished: testAndroidTestCaseSetupProperly(com.tut.my.service.MyServiceTest)
I/TestRunner(11954): passed: testAndroidTestCaseSetupProperly(com.tut.my.service.MyServiceTest)
I/ActivityManager(71): Force stopping package com.tut.my.service uid=10036
I/Process(71): Sending signal. PID: 11954 SIG: 9

問題は、なぜ testServiceTestCaseSetupProperly() が最初ではなく最後に呼び出されるのかということです。そして、MyService オブジェクトがあまりにも無残に死ぬ理由。

編集:より正確にするには:

私の懸念の重要な部分は、onCreate への失礼な呼び出しです。

 I/TestRunner(11954): started: testServiceTestCaseSetUpProperly(com.tut.my.service.MyServiceTest)
 D/MyService(11954): called: std c-tor() <--- ONLY one call to onCreate
 I/TestRunner(11954): finished:testServiceTestCaseSetUpProperly(com.tut.my.service.MyServiceTest)
  • onCreate でリソースを割り当てる場合、割り当てられたリソースをクリーンアップするように誰が主張しますか?
  • すべてのテストの最後に、適切なサービス設定のチェックが開始されるのはなぜですか?
  • とにかく殺されるのはなぜですか?
4

1 に答える 1

2

JUnit 3 はリフレクションを使用して、実行するテストを取得します。テストが特定の順序で実行されることは保証されていません。さらに、単体テストは互いに独立している必要があるため、実行順序は関係ありません。

于 2012-07-16T06:29:56.167 に答える