Использование встроенных Jasmine ассертов

Protractor изначально проектировался как end-to-end фреймворк поверх Jasmine. Jasmine отвечает за структуру тестов, жизненный цикл, ассерты и отчётность. Встроенные ассерты Jasmine являются базовым инструментом проверки состояния приложения: они определяют, считается ли тест пройденным или проваленным.

Ассерты Jasmine основаны на механизме expect, который принимает фактическое значение и сравнивает его с ожидаемым через matcher (матчер). В контексте Protractor это особенно важно, поскольку фактические значения часто получаются асинхронно из браузера.


Общий принцип работы ассертов

Базовая форма ассерта:

expect(actual).matcher(expected);
  • actual — фактическое значение (результат действия, текст элемента, состояние страницы)
  • matcher — правило сравнения
  • expected — ожидаемое значение

Jasmine автоматически выбрасывает ошибку при несовпадении, что приводит к падению теста. В Protractor это поведение интегрировано с WebDriverJS и учитывает ожидание выполнения промисов.


Автоматическая обработка асинхронности в Protractor

Классическая проблема end-to-end тестирования — асинхронные операции. Protractor (до версии 6) использует Control Flow, позволяющий писать ассерты без явного then:

expect(element(by.id('title')).getText()).toEqual('Dashboard');

getText() возвращает Promise, но Jasmine получает уже разрешённое значение. Это делает ассерты декларативными и читаемыми. В окружениях без Control Flow (или при его отключении) используется async/await:

const title = await element(by.id('title')).getText();
expect(title).toEqual('Dashboard');

Основные matcher’ы сравнения

toEqual

Глубокое сравнение значений. Используется для строк, чисел, массивов и объектов.

expect(userName).toEqual('admin');

Для объектов сравниваются все поля рекурсивно.

toBe

Строгое сравнение (===). Применяется, когда важно сравнить именно ссылку или примитив без приведения типов.

expect(isLoggedIn).toBe(true);

toBeTruthy / toBeFalsy

Проверка логического значения без строгого сравнения с true или false.

expect(elementPresent).toBeTruthy();

Часто используется при проверке существования элементов или состояний.


Ассерты для проверки DOM-состояния

Проверка наличия элемента

expect(element(by.css('.error')).isPresent()).toBe(true);

isPresent() проверяет существование элемента в DOM, а не его видимость.

Проверка видимости

expect(element(by.id('submit')).isDisplayed()).toBe(true);

Ассерт падает, если элемент скрыт через CSS или отсутствует.

Проверка доступности (enabled/disabled)

expect(button.isEnabled()).toBe(false);

Используется для валидации форм и интерактивных состояний.


Ассерты для строк и шаблонов

toContain

Проверка, что строка содержит подстроку.

expect(message.getText()).toContain('успешно');

Полезно при динамических текстах, уведомлениях, логах.

toMatch

Сравнение по регулярному выражению.

expect(url).toMatch(/\/dashboard$/);

Используется для проверки URL, форматов дат, сообщений об ошибках.


Числовые сравнения

toBeGreaterThan / toBeLessThan

expect(itemsCount).toBeGreaterThan(0);

Применяется при проверке количества элементов, размеров списков, числовых метрик.

toBeCloseTo

Сравнение чисел с допустимой погрешностью.

expect(price).toBeCloseTo(9.99, 2);

Актуально для значений, полученных из расчётов или API.


Ассерты для коллекций элементов

Protractor возвращает ElementArrayFinder для множественных элементов.

Проверка количества элементов

expect(element.all(by.css('.row')).count()).toBe(5);

Проверка конкретного элемента коллекции

expect(rows.get(0).getText()).toContain('ID');

Коллекции можно комбинировать с любыми matcher’ами Jasmine.


Негативные ассерты

Любой matcher может быть инвертирован через not.

expect(errorMessage.isPresent()).not.toBe(true);
expect(title).not.toEqual('Login');

Негативные проверки важны при тестировании отказов, ошибок валидации и недопустимых состояний.


Пользовательские matcher’ы Jasmine

Jasmine позволяет расширять стандартный набор matcher’ов, что полезно для сложных проверок в Protractor.

Пример добавления matcher’а:

beforeEach(() => {
  jasmine.addMatchers({
    toHaveClass: () => ({
      compare: (element, expectedClass) => {
        return {
          pass: element.getAttribute('class')
            .then(classes => classes.split(' ').includes(expectedClass))
        };
      }
    })
  });
});

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

expect(button).toHaveClass('active');

Пользовательские matcher’ы повышают читаемость тестов и снижают дублирование логики.


Сообщения об ошибках и читаемость отчётов

Jasmine автоматически формирует сообщения об ошибках, включая фактическое и ожидаемое значение. Для сложных сценариев это критично при анализе падений в CI.

Пример сообщения:

Expected 'Error 500' to contain 'успешно'

Чётко сформулированные ассерты упрощают диагностику проблем в end-to-end тестах.


Ассерты и ожидания (ExpectedConditions)

Ассерты проверяют состояние, но не ждут его изменения. В Protractor часто используется связка ожиданий и ассертов:

const EC = protractor.ExpectedConditions;
browser.wait(EC.visibilityOf(message), 5000);
expect(message.getText()).toContain('Готово');

Ожидание гарантирует, что ассерт выполняется в корректный момент времени.


Типичные ошибки при использовании ассертов

  • Проверка состояния без ожиданий при асинхронных изменениях DOM
  • Использование toBe вместо toEqual для объектов и строк
  • Ассерты на точное совпадение текста там, где текст динамический
  • Проверка isPresent() вместо isDisplayed() для UI-сценариев

Корректный выбор matcher’а напрямую влияет на стабильность тестов.


Практическая роль ассертов в end-to-end тестах

Ассерты Jasmine в Protractor выполняют функцию контракта между тестом и приложением. Они фиксируют ожидаемое поведение интерфейса, бизнес-логики и пользовательских сценариев. Грамотное использование стандартных matcher’ов снижает количество флапающих тестов и повышает ценность автоматизации как инструмента контроля качества.