Подтвердить что ты не робот

Как имитировать контакт с фоновым сервисом с помощью sendevent или другим способом?

Можно ли имитировать касание от фонового приложения (или службы) или запустить sh script (который имитирует касание)?

Он необходим для тестирования системы Android без USB или другого подключения к ПК, поэтому я не могу (или не знаю, как) использовать обезьяны или другие средства автотеста.

Добавлена ​​информация: Я нашел способ запуска команд оболочки с корнем (проверенные корневые устройства):

Невозможно выполнить команду sendevent shell через код Android (создать сенсорное моделирование). Запись файла в системный раздел (запуск команд с правами root)

Также я получаю события для имитации касания.

В результате я:

//sendevent commands to simulate touch (verify it work from cmd)
String[] touchEvent = { "sendevent /dev/input/event0 0 0 0\n",
                        "sendevent /dev/input/event6 3 53 499\n",
                        "sendevent /dev/input/event6 3 54 680\n",
                        "sendevent /dev/input/event6 3 58 40\n",
                        "sendevent /dev/input/event6 3 48 3\n",
                        "sendevent /dev/input/event6 3 57 0\n",
                        "sendevent /dev/input/event6 0 2 0\n",
                        "sendevent /dev/input/event6 0 0 0\n",
                        "sendevent /dev/input/event6 0 2 0\n",
                        "sendevent /dev/input/event6 0 0 0\n",
                        "sendevent /dev/input/event0 3 0 2\n",
                        "sendevent /dev/input/event0 0 0 0\n"};

try{
    Thread.sleep(2000);
    Process root = Runtime.getRuntime().exec("su");
    DataOutputStream os = new DataOutputStream(root.getOutputStream());             
    for(int i = 0; i < touchEvent.length; i++){
            Log.i(TAG, touchEvent[i]);  
            os.writeBytes(touchEvent[i]);
            os.flush();
    }
    root.waitFor();
} catch (IOException e) {
    Log.e(TAG, "Runtime problems\n");
    e.printStackTrace();
} catch (SecurityException se){
    se.printStackTrace();
} catch (InterruptedException e) {
    e.printStackTrace();
}

У меня нет никаких исключений, но это не касается имитации.

Помогает ли кто-нибудь решить эту проблему?

Если есть еще один способ сделать это с помощью андроида ndk или демона на C, сообщите мне об этом.

Спасибо.

4b9b3361

Ответ 1

Я не могу выполнить команду "sendevent", но нашел другой способ для себя, надеюсь, что это будет полезно для кого-то.

Для имитации touch я использовал sendPointerSync() из android.app.Instrumentation, которые работают только с разрешением "android.permission.INJECT_EVENTS". Для его использования вы должны скомпилировать свое приложение как системное приложение. Чтобы сделать это, вы должны выполнить следующие шаги:

  • Получение файлов из источника android:

    корневой из-андроида-источник-дерево/выход/хост//структура/signapk.jar

    корневой из-андроид-источник-дерево/строительство/цели/продукт/безопасность/platform.x509.pem

    корневой из-андроид-источник-дерево/строительство/цели/продукт/безопасность/platform.pk8

  • Подпишите свое приложение, используя файлы:

    Команда " java -jar signapk.jar platform.x509.pem platform.pk8 YourApp-unsigned.apk" YourApp-signed.apk.

  • adb install YourApp-signed.apk
    • Запустите приложение
    • Используйте "adb shell ps", чтобы подтвердить, что ваше приложение работает как система.

Код с симуляцией касания (для моделирования нужен новый поток):

Thread thread = new Thread(){
       @Override
       public void run(){
               Instrumentation m_Instrumentation = new Instrumentation();

               m_Instrumentation.sendPointerSync(MotionEvent.obtain(
                       SystemClock.uptimeMillis(),
                       SystemClock.uptimeMillis(),
                       MotionEvent.ACTION_DOWN,posx, posy, 0));
               m_Instrumentation.sendPointerSync(MotionEvent.obtain(
                       SystemClock.uptimeMillis(),
                       SystemClock.uptimeMillis(),
                       MotionEvent.ACTION_UP,width*4/5,height, 0));
       }
   };

манифеста:

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.example.yourapp"
    **android:sharedUserId="android.uid.system"**
    android:versionCode="1"
    android:versionName="1.0" >

      

Использование ресурсов:

Ответ 2

Я собирался реализовать свое решение, когда нашел более простой вариант - размещение в надежде, что это будет полезно кому-то. Поскольку у вас уже есть внедренное устройство, вам не нужно подписывать его как системное приложение.

Для имитации касания в позиции (100,200) все, что вам нужно, это вызов ввода из службы, используя Runtime.exec следующим образом:

Process process = Runtime.getRuntime().exec("su");
DataOutputStream os = new DataOutputStream(process.getOutputStream());
String cmd = "/system/bin/input tap 100 200\n";
os.writeBytes(cmd);
os.writeBytes("exit\n");
os.flush();
os.close();
process.waitFor();

Ответ 3

Вы можете использовать "салфетки". Глядя на исходный код Input.java, вы можете увидеть необходимые параметры для прокрутки.

Вот gist, который я сделал для моделирования салфетки, для воспроизведения smove game с кликами вместо проверок, чтобы проверить это. Для использования этой реализации вам нужен суперпользователь.