通过节点使用 shell 命令启动 Android 模拟器时的回调

Callback when starting Android emulator with shell command via node

我正在通过 shell 脚本打开带有节点的 android 模拟器:

var process = require('child_process');

process.exec('~/Library/Android/sdk/tools/emulator -avd Nexus_5_API_21_x86', processed);

function processed(data){
    console.log('processed called', data, data.toString());
}

我需要能够检测到模拟器何时完成加载,以便我可以启动屏幕解锁,然后将浏览器启动到指定的 url(~/Library/Android/sdk/platform-tools/adb shell input keyevent 82~/Library/Android/sdk/platform-tools/adb shell am start -a android.intent.action.VIEW -d http://www.whosebug.com )

但是,当我启动模拟器时,我似乎没有得到任何回复,并且该进程与模拟器保持交互。当关闭进程(ctrl+c)时,模拟器也随之关闭。 (这与直接在终端中 运行ning shell 命令的行为相同)

  1. 是否可以知道模拟器何时打开并加载?

  2. 进程继续执行时如何执行附加命令 运行?

老大解决了

我能够设置一个计时器,每秒检查一次启动动画是否已停止。如果有,我们知道模拟器已打开并启动。

var process         = require('child_process');

process.exec('~/Library/Android/sdk/tools/emulator -avd Nexus_5_API_21_x86');

function isEmulatorBooted(){
    process.exec('~/Library/Android/sdk/platform-tools/adb shell getprop init.svc.bootanim', function(error, stdout, stderr){

        if (stdout.toString().indexOf("stopped")>-1){

            clearInterval(bootChecker);
            emulatorIsBooted();
        } else {
            console.log('we are still loading');
        }
    });
}

function emulatorIsBooted(){
    //unlock the device
    process.exec('~/Library/Android/sdk/platform-tools/adb shell input keyevent 82');

    //gotourl
    process.exec('~/Library/Android/sdk/platform-tools/adb shell am start -a android.intent.action.VIEW -d http://192.168.10.126:9876/');
}

bootChecker = setInterval(function(){
    isEmulatorBooted();
},1000);

如果其他人正在寻找这个,请制作 Fraser 脚本的替代版本 - 它也会在后台进程中启动实际的模拟器。

#!/usr/bin/env node

const process = require('child_process');

/* Get last emulator in list of emulators */
process.exec("emulator -list-avds|sed '$!d'", (_, stdout) => {
  console.log('[android emulator] Booting')

  /* Start emulator */
  process.exec(`nohup emulator -avd ${stdout.replace('\n', '')} >/dev/null 2>&1 &`)

  /* Wait for emulator to boot */
  const waitUntilBootedThen = completion => {
    process.exec('adb shell getprop init.svc.bootanim', (_, stdout) => {
      if (stdout.replace('\n', '') !== 'stopped') {
        setTimeout(() => waitUntilBootedThen(completion), 250)
      } else {
        completion()
      }
    })
  }

  /* When emulator is booted up */
  waitUntilBootedThen(() => {
    console.log('[android emulator] Done')
  })
})