by.model() — это локатор в Protractor, который
предназначен исключительно для приложений на Angular. Он используется
для поиска элементов, связанных с Angular-моделью
данных, указанной в атрибуте ng-model. Такой
подход позволяет напрямую взаимодействовать с данными модели, минуя
сложные селекторы по CSS или XPath, что делает тесты более стабильными и
читаемыми.
Атрибут ng-model в Angular связывает элемент формы с
конкретной переменной в $scope. Например:
<input type="text" ng-model="user.name">
Чтобы получить доступ к этому элементу в Protractor, используется:
let nameInput = element(by.model('user.name'));
После этого можно применять стандартные методы взаимодействия с элементами:
nameInput.sendKeys('Иван');
nameInput.clear();
expect(nameInput.getAttribute('value')).toEqual('Иван');
Ключевой момент: by.model() работает только с Angular-приложениями, поскольку Protractor ориентируется на Angular-структуру и ожидания завершения асинхронных операций внутри фреймворка.
element(by.model('user.address.street')).sendKeys('Ленина, 10');
ng-model,
element(by.model(...)) вернет первый
элемент, а для получения всех подходящих элементов применяется
element.all(by.model(...)):let checkboxes = element.all(by.model('task.completed'));
checkboxes.each(cb => cb.click());
by.model() применим к <input>,
<textarea>, <select>,
<checkbox>, <radio> — везде, где
используется ng-model.Protractor автоматически синхронизируется с Angular и ожидает
завершения асинхронных операций перед взаимодействием с элементами. При
использовании by.model() это позволяет безопасно вводить
данные или получать их значение без явного ожидания:
element(by.model('user.email')).sendKeys('test@example.com');
expect(element(by.model('user.email')).getAttribute('value')).toEqual('test@example.com');
В редких случаях, если тесты выполняются в приложении с внешними
AJAX-запросами вне Angular, может потребоваться использование
browser.wait для явного ожидания.
element(by.model('user.name')).sendKeys('Иван');
element(by.model('user.email')).sendKeys('ivan@example.com');
expect(element(by.model('user.name')).getAttribute('value')).toEqual('Иван');
expect(element(by.model('user.email')).getAttribute('value')).toEqual('ivan@example.com');
element(by.model('user.subscribe')).click(); // чекбокс
element(by.model('user.gender')).element(by.css('option[value="male"]')).click(); // select
element.all(by.model('task.completed')).each(function(checkbox) {
checkbox.isSelected().then(function(selected) {
if (!selected) {
checkbox.click();
}
});
});
ng-model.by.css или
by.xpath.ng-model
для нескольких элементов лучше применять element.all с
фильтрацией.Использование by.model() в тестах Protractor позволяет
создавать стабильные, читаемые и поддерживаемые
автотесты для Angular-приложений, минимизируя зависимость от
структуры DOM и упрощая взаимодействие с формами и данными модели.