Рано или поздно любой тестер, развивающий практики автотестирования, сталкивается с проблемой автономного выполнения своих тестов. Причем, если специалист опытный, то он старается столкнуться с этим как можно раньше. Так и я, после первого успешного прогона автотеста локально, решил сразу настроить запуск в TeamCity.
Отмечу, что у нас в компании экспертизы по удаленному запуску инструментальных тестов Android практически нет, поэтому приходилось усердно гуглить, но и там развернутых гайдов не нашел. Посему и решил запилить данную инструкцию.
На входе имеем:
Сразу дисклеймер по поводу сервера, где будет осуществляться запуск: настройка ОС, аппаратной виртуализации и графической оболочки не является предметом данной статьи и будет опущена.
Начнем с Java. Тут главное правильно выбрать версию. У меня было 3 зависимости: сами тесты, android tools и агент teamcity. Остановился на версии 8, чтобы пользоваться одной JVM для всех. Если вам повезет меньше, и будут конфликты, то придется настраивать использование нескольких версий Java на одной машине. Еще заметка: если у вас debian, то сначала нужно добавить репозиорий webupd8team (гуглится очень быстро).
Далее создаем пользователя, под которым будет запускаться агент и, соответственно, все остальное. Не забываем задать пароль.
Дистрибутив агента можно взять в веб интерфейсе вашего teamcity. Для этого перейдите в раздел Agents и справа вверху нажмите ссылку Install Build Agents. Скачайте и распакуйте в нужную папку на сервере (я рекомендую домашнюю папку нашего юзера —
Если ваша версия teamcity поддерживает Agent Push, то все еще проще. Просто откройте соответствующую вкладку в веб интерфейсе, нажмите кнопку Install Agent... и следуйте инструкциям.
Настраиваем конфиг. Если вы пользовались удаленной установкой, то он уже создан и в нем нужно только задать имя агента. Если нет, то создаем:
Заполняем
Запускаем командой
Для автоматического запуска агента создаем скрипт
Добавляем права на запуск
Контрольная перезагрузка, агент поднялся, едем дальше.
Скачиваем android sdk tools (Command line tools only) и распаковываем в нужную директорию. Создаем директорию для хранения будущих образов AVD (место должно быть достаточно). Для меня админы подключили основное хранилище в каталог
Добавляем переменные среды. Открываем на редактирование файл
Перезагружаем и проверяем, что переменные корректно отображаются в веб интерфейсе teamcity на вкладке Agent Parameters.
Пробуем запустить sdkmanager: команда
Устанавливаем необходимые тулы и образ(-ы) виртуалок.
Итак, скачали образ
Передаем имя и исходный образ (должен быть скачен заранее через sdkmanager). Если вернулась ошибка, то добавьте флаг
Переходим к эмулятору. Для начала проверьте наличие папок emulator, platforms, platform-tools, system-images в директории SDK. platforms я создал руками, остальные создались при установке пакетов через sdkmanager. Далее проверим аппаратное ускорение. Должен быть такой ответ.
Если будет ошибка доступа к
Плюс мне еще потребовалось установить QEMU:
Делаем релогон и проверяем эмулятор еще раз.
Если все ок, то пробуем запустить. Чтобы посмотреть глазами, подключимся к серверу по vnc. И запустим эмулятор:
Должно появиться такое окно:
Во время прогонов тестов будем запускать без графики, поэтому добавим параметр
Переходим к завершающему этапу — настройке автономного запуска наших тестов. У меня получился билд из 4 шагов.
1. Запуск эмулятора
Так как эмулятор «лочит» терминал, нужно отвязать процесс с помощью утилиты nohup (можно и по-другому — решать вам). На всякий случай сохраняем лог эмулятора в файл
2. Ожидание загрузки устройства.
Сначала ждем статус
3. Запуск тестов. Здесь все индивидуально, вот мой пример:
4. Закрываем эмулятор. Здесь пока сделал простое терминирование процесса.
Но лучше, конечно, запоминать ID процесса при создании эмулятора. Это нужно будет когда начнем запускать тесты в несколько потоков, что случайно не «убить» не тот процесс.
На этом все, спасибо, что дочитали. Если будут замечания от более опытных коллег, то с удовольствием внесу правки в мануал.
Отмечу, что у нас в компании экспертизы по удаленному запуску инструментальных тестов Android практически нет, поэтому приходилось усердно гуглить, но и там развернутых гайдов не нашел. Посему и решил запилить данную инструкцию.
На входе имеем:
- тест(-ы), успешно запускаемый локально
- работающий сервер TeamCity
- сервер на debian с KVM и иксами
Сразу дисклеймер по поводу сервера, где будет осуществляться запуск: настройка ОС, аппаратной виртуализации и графической оболочки не является предметом данной статьи и будет опущена.
Установка и настройка агента TeamCity
Начнем с Java. Тут главное правильно выбрать версию. У меня было 3 зависимости: сами тесты, android tools и агент teamcity. Остановился на версии 8, чтобы пользоваться одной JVM для всех. Если вам повезет меньше, и будут конфликты, то придется настраивать использование нескольких версий Java на одной машине. Еще заметка: если у вас debian, то сначала нужно добавить репозиорий webupd8team (гуглится очень быстро).
sudo apt-get install oracle-java8-installer
sudo apt-get install oracle-java8-set-default
Далее создаем пользователя, под которым будет запускаться агент и, соответственно, все остальное. Не забываем задать пароль.
sudo useradd -d /home/tc_agent -s /bin/bash -m tc_agent
sudo passwd tc_agent
Дистрибутив агента можно взять в веб интерфейсе вашего teamcity. Для этого перейдите в раздел Agents и справа вверху нажмите ссылку Install Build Agents. Скачайте и распакуйте в нужную папку на сервере (я рекомендую домашнюю папку нашего юзера —
/home/tc_agent
). Далее добавьте права на запуск всем скриптам: sudo chmod +x /home/tc_agent/BuildAgent/bin/*
Если ваша версия teamcity поддерживает Agent Push, то все еще проще. Просто откройте соответствующую вкладку в веб интерфейсе, нажмите кнопку Install Agent... и следуйте инструкциям.
Настраиваем конфиг. Если вы пользовались удаленной установкой, то он уже создан и в нем нужно только задать имя агента. Если нет, то создаем:
cd /home/tc_agent/BuildAgent/conf
cp buildAgent.dist.properties buildAgent.properties
nano buildAgent.properties
Заполняем
serverUrl=
адресом веб интерфейса сервера, а name=
уникальным именем агента. Если у вас несколько агентов или дефолтный порт (9090) занят, то задайте свой с помощью параметра ownPort=
.Запускаем командой
/home/tc_agent/BuildAgent/bin/agent.sh start
. Если все настроено верно, то увидим наш агент на вкладке Unauthorized. Авторизовываем и можно пользоваться.Для автоматического запуска агента создаем скрипт
/etc/init.d/teamcity_agent
со следующим содержимым:#!/bin/bash
BINARY="/home/tc_agent/BuildAgent/bin/agent.sh"
RUNAS="tc_agent"
LOGFILE="/home/tc_agent/BuildAgent/logs/start.log"
CMD="$BINARY $1 $2"
runuser - "$RUNAS" -c "$CMD > $LOGFILE"
cat $LOGFILE
Добавляем права на запуск
sudo chmod +x /etc/init.d/teamcity_agent
и добавляем строку /etc/init.d/teamcity_agent start
в файл /etc/rc.local
.Контрольная перезагрузка, агент поднялся, едем дальше.
Установка Android SDK и эмулятора
Скачиваем android sdk tools (Command line tools only) и распаковываем в нужную директорию. Создаем директорию для хранения будущих образов AVD (место должно быть достаточно). Для меня админы подключили основное хранилище в каталог
/var,
туда и буду все складывать. Далее меняем владельца файлов на нашего пользователя и последующие действия лучше делать под ним.sudo chown tc_agent -R /var/opt/android-sdk
sudo mkdir /var/opt/.android
sudo chown tc_agent /var/opt/.android
Добавляем переменные среды. Открываем на редактирование файл
/home/tc_agent/.bash_profile
и прописываем:export ANDROID_HOME=/var/opt/android-sdk
export ANDROID_AVD_HOME=/var/opt/.android/avd
export PATH=$ANDROID_HOME/platform-tools:$PATH
export PATH=$ANDROID_HOME/tools:$PATH
Перезагружаем и проверяем, что переменные корректно отображаются в веб интерфейсе teamcity на вкладке Agent Parameters.
Пробуем запустить sdkmanager: команда
$ANDROID_HOME/tools/bin/sdkmanager --list
должна вывести список установленных и доступных пакетов. Если получили ошибку вида Exception in thread "main" java.lang.NoClassDefFoundError
, то попробуйте это решение.Устанавливаем необходимые тулы и образ(-ы) виртуалок.
$ANDROID_HOME/tools/bin/sdkmanager emulator platform-tools tools
$ANDROID_HOME/tools/bin/sdkmanager 'system-images;android-25;google_apis;x86'
Создание и запуск AVD
Итак, скачали образ
'system-images;android-25;google_apis;x86'
(Android 7.1.1), создадим на его основе виртуальное устройство. Не буду вдаваться в подробности всех возможных параметров утилиты avdmanager, покажу на минимально возможном количестве:$ANDROID_HOME/tools/bin/avdmanager create avd -n avd_name -k "system-images;android-25;google_apis;x86"
Передаем имя и исходный образ (должен быть скачен заранее через sdkmanager). Если вернулась ошибка, то добавьте флаг
-v
, чтобы посмотреть текст.Переходим к эмулятору. Для начала проверьте наличие папок emulator, platforms, platform-tools, system-images в директории SDK. platforms я создал руками, остальные создались при установке пакетов через sdkmanager. Далее проверим аппаратное ускорение. Должен быть такой ответ.
$ANDROID_HOME/emulator/emulator -accel-check
accel:
0
KVM (version 12) is installed and usable.
accel
Если будет ошибка доступа к
/dev/kvm
, то добавляем права:addgroup kvm
usermod -a -G kvm tc_agent
chown root:kvm /dev/kvm
Плюс мне еще потребовалось установить QEMU:
sudo apt-get install qemu-kvm
Делаем релогон и проверяем эмулятор еще раз.
Если все ок, то пробуем запустить. Чтобы посмотреть глазами, подключимся к серверу по vnc. И запустим эмулятор:
$ANDROID_HOME/emulator/emulator @avd_name
Должно появиться такое окно:
Во время прогонов тестов будем запускать без графики, поэтому добавим параметр
-no-window
.Настраиваем build в TeamCity
Переходим к завершающему этапу — настройке автономного запуска наших тестов. У меня получился билд из 4 шагов.
1. Запуск эмулятора
nohup /var/opt/android-sdk/emulator/emulator @avd_name -no-snapshot-save -no-boot-anim -no-window -snapshot clean_snap_1 > start_emulator.log 2>&1&
Так как эмулятор «лочит» терминал, нужно отвязать процесс с помощью утилиты nohup (можно и по-другому — решать вам). На всякий случай сохраняем лог эмулятора в файл
start_emulator.log
. Для запуска тестов я создал чистый снапшот (как это сделать читайте здесь) и добавил ключ -no-snapshot-save
, чтобы он не перезаписывался.2. Ожидание загрузки устройства.
adb wait-for-device shell 'while [[ -z $(getprop sys.boot_completed) ]]; do sleep 1; done;'
Сначала ждем статус
wait-for-device
, затем в цикле ждем когда переменная sys.boot_completed
вернет 1.3. Запуск тестов. Здесь все индивидуально, вот мой пример:
./gradlew clean connectedAndroidTest
4. Закрываем эмулятор. Здесь пока сделал простое терминирование процесса.
kill -s 2 `pgrep qemu-system`
Но лучше, конечно, запоминать ID процесса при создании эмулятора. Это нужно будет когда начнем запускать тесты в несколько потоков, что случайно не «убить» не тот процесс.
На этом все, спасибо, что дочитали. Если будут замечания от более опытных коллег, то с удовольствием внесу правки в мануал.