Интеграция с Jasmine

Karma — это тест-раннер для JavaScript, обеспечивающий запуск тестов в реальных браузерах с возможностью интеграции с различными фреймворками тестирования, включая Jasmine. Для начала работы необходимо установить пакет Karma и соответствующие плагины:

npm install --save-dev karma karma-jasmine jasmine-core karma-chrome-launcher
  • karma — ядро тест-раннера.
  • karma-jasmine — адаптер для Jasmine.
  • jasmine-core — сама библиотека Jasmine.
  • karma-chrome-launcher — позволяет запускать тесты в браузере Chrome.

После установки создается конфигурационный файл Karma:

npx karma init

В процессе инициализации выбирается фреймворк тестирования (jasmine), браузеры для запуска тестов и файлы, которые будут включены в тестовый пакет.


Конфигурация файлов

Файл karma.conf.js определяет ключевые аспекты работы тест-раннера. Пример базовой конфигурации для Jasmine:

module.exports = function(config) {
  config.set({
    frameworks: ['jasmine'],
    files: [
      'src/**/*.js',
      'test/**/*.spec.js'
    ],
    exclude: [],
    preprocessors: {},
    reporters: ['progress'],
    port: 9876,
    colors: true,
    logLevel: config.LOG_INFO,
    autoWatch: true,
    browsers: ['Chrome'],
    singleRun: false,
    concurrency: Infinity
  });
};

Ключевые моменты:

  • frameworks — указывает Jasmine как фреймворк для тестов.
  • files — список файлов, которые будут загружены в браузер перед запуском тестов. Обычно это исходники и файлы с тестами.
  • reporters — формат вывода результатов (например, progress, dots).
  • browsers — браузеры для запуска тестов. Можно использовать Chrome, Firefox или Headless-браузеры для CI/CD.
  • autoWatch — если true, Karma автоматически запускает тесты при изменении файлов.
  • singleRun — режим однократного запуска (важно для CI).

Структура тестов в Jasmine

Jasmine использует описательную структуру тестов через функции describe и it.

describe('Функция суммирования', () => {
  it('должна возвращать сумму двух чисел', () => {
    const sum = (a, b) => a + b;
    expect(sum(2, 3)).toBe(5);
  });

  it('должна корректно работать с отрицательными числами', () => {
    const sum = (a, b) => a + b;
    expect(sum(-1, -4)).toBe(-5);
  });
});
  • describe группирует тесты по функциональности.
  • it описывает отдельный тестовый случай.
  • expect формирует утверждения, которые проверяют поведение кода.

Асинхронное тестирование

Jasmine поддерживает асинхронные тесты через колбэки, промисы или async/await.

С использованием done:

it('должна завершиться после таймера', (done) => {
  setTimeout(() => {
    expect(true).toBe(true);
    done();
  }, 1000);
});

С использованием промисов:

it('возвращает данные с сервера', () => {
  return fetchData().then(data => {
    expect(data).toBeDefined();
  });
});

С использованием async/await:

it('должна получить данные', async () => {
  const data = await fetchData();
  expect(data).toBeDefined();
});

Моки и шпионы

Jasmine позволяет создавать шпионы (spy) для отслеживания вызовов функций или замены их поведения.

describe('Тестирование функции логирования', () => {
  it('должна вызвать console.log', () => {
    spyOn(console, 'log');
    logMessage('Привет');
    expect(console.log).toHaveBeenCalledWith('Привет');
  });
});

Основные функции шпионов:

  • spyOn(obj, 'method') — заменяет метод объекта шпионом.
  • and.callFake(fn) — позволяет подменить реализацию метода.
  • and.returnValue(value) — возвращает фиксированное значение.
  • toHaveBeenCalled() и toHaveBeenCalledWith() — проверка вызовов.

Интеграция с CI/CD

Karma легко интегрируется в автоматизированные сборки. Для этого обычно используется режим singleRun: true с Headless-браузерами:

browsers: ['ChromeHeadless'],
singleRun: true,

Запуск тестов через командную строку:

npx karma start

В CI-системах (Jenkins, GitLab CI, GitHub Actions) рекомендуется использовать Headless Chrome для минимизации ресурсов и автоматического завершения тестов.


Расширение функционала

Karma поддерживает плагины для:

  • Отчеты о покрытии кодаkarma-coverage.
  • Препроцессоры для TypeScript и Babelkarma-webpack, karma-typescript.
  • Различные браузеры и эмуляторыkarma-firefox-launcher, karma-safari-launcher, karma-sauce-launcher.

Пример конфигурации с покрытием кода:

preprocessors: {
  'src/**/*.js': ['coverage']
},
reporters: ['progress', 'coverage'],
coverageReporter: {
  type: 'html',
  dir: 'coverage/'
}

Это позволяет генерировать отчеты в HTML и интегрировать их в процесс разработки и CI.


Практические рекомендации

  • Структурировать тесты по модулям, чтобы describe отражал функциональные блоки.
  • Использовать шпионы для внешних зависимостей и побочных эффектов.
  • Разделять синхронные и асинхронные тесты, чтобы избежать неожиданных ошибок.
  • Подключать только необходимые файлы и зависимости для ускорения запуска Karma.
  • Автоматизировать запуск тестов через npm scripts:
"scripts": {
  "test": "karma start karma.conf.js"
}
  • Постоянно проверять совместимость плагинов Karma с версией Jasmine и браузеров.

Эта интеграция Jasmine с Karma обеспечивает надёжный и масштабируемый процесс тестирования, поддерживает асинхронные сценарии, отслеживание вызовов функций и возможность полной автоматизации в CI/CD средах.